2013-08-29 3 views
0

현재 Accelerated C++를 사용 중이며 CH11에 내 버전을 만들려고합니다. 소멸자를 통해 메모리를 할당 해제하려고 할 때 비어있는 "Vec"를 만들거나 푸시 백을 사용하여 읽기 액세스 메모리를 얻습니다. 나는 내가 무엇을 놓쳤는 지 정말로 모른다. 도움 주셔서 감사합니다.메모리 할당 해제시 액세스 위반이 발생했습니다.

#include "Vec.h" 
int main() 
{ 
Vec<int> v; 

return 0; 
} 

/////////

두 생성자 SB가 create() 이전에 사용되는 지적 이니셜 라이저 목록 이전 사용에 (자신의 멤버를 초기화해야
#include <algorithm> 
#include <cstddef> 
#include <memory> 


using std::max; 

///////////////////////////// 
template <class T> class Vec { 
public: 
    typedef T* iterator; 
    typedef const T* const_iterator; 
    typedef size_t size_type; 
    typedef T value_type; 
    typedef T& reference; 
    typedef const T& const_reference; 

    //Constructor 
    Vec() { create();} 
    explicit Vec(size_type n, const T& = T()) {create(n,t);} 

    //Copy 
    Vec(const Vec& v) {create(v.begin(), v.end());} 
    //Assignment 
    Vec& operator=(const Vec&); 
    //Destructor 
    ~Vec() { uncreate();} 

    //Indexing 
    T& operator[](size_type i) {return data[i]; } 
    const T& operator[](size_type i) const { return data[i]; } 



    //Size 
    size_type size() const { return avail - data; } 

    //Return member variables 
    iterator begin() { return data; } 
    const_iterator begin() const { return data; } 

    iterator end() { return avail; } 
    const_iterator end() const {return avail; } 

    //Uncreate 
    void clear() { uncreate(); } 
    //Check empty 
    bool empty() const { return data == avail; } 
////////////////////// 
private: 
    iterator data; //first 
    iterator avail; //(one past) last element 
    iterator limit; //(one past) allocated memory 

    std::allocator<T> alloc; // object for memory allocation 

    //allocate and initialize thorugh constructors 
    void create(); 
    void create(size_type, const T&); 
    void create(const_iterator, const_iterator); 

    //destory 
    void uncreate(); 


}; 
//////////////////////////// 
template <class T> void Vec<T>::create() 
{ 
    data = avail = limit; 
} 

template <class T> void Vec<T>::create(size_type n, const T& val) 
{ 
    data = alloc.allocate(n , 0); 
    limit = avail = data + n; 
    std::uninitialized_fill(data, limit, val); 
} 

template <class T> void Vec<T>::create(const_iterator i, const_iterator j) 
{ 
    data = alloc.allocate(j - i, 0); 
    limit = avail = std::uninitialized_copy(i , j, data); 
} 

template <class T> void Vec<T>::uncreate() 
{ 
    if(data) { 
     iterator it = avail; 
     while(it != data) 
      alloc.destroy(--it); 
     alloc.deallocate(data, limit - data); 
    } 
    data = limit = avail = 0; 
} 
+3

'데이터 = 소용 = 제한하고, '당신은 GDB를 시도? –

+0

'Vec'의 생성자에서'create (n, t)'가 참조됩니다. 이러한 't'는 매개 변수에 제공되지 않습니다. 컴파일 가능하도록 업데이트하십시오. – WhozCraig

+0

메모리를 할당하지 않는'create()'를 통해 빈'Vec '을 생성하고 있습니다. '~ Vec()'에서'uncreate()'를 호출 할 때 메모리를 전혀 할당 해제하지 않는다는 사실에 놀라지 않을까요? 당신의'data'는'nullptr'이 아닙니다. ** SB. **가 맞아야합니다. – lapk

답변

0

결정된 값들이 할당 됨). 소멸자가 해고되면 당신은 불확정 포인터 값을 사용하고 그것을 할당 해제하기 위해 보낼 수 있습니다.

변경이 : 여기에

Vec() { create();} 
explicit Vec(size_type n, const T& = T()) {create(n,t);} 

:`생성()`초기화되지 않은 값을 사용 할 수있는

Vec() : data(), avail(), limit() { create();} 
explicit Vec(size_type n, const T& t = T()) 
    : data(), avail(), limit() {create(n,t);} 
+0

첫 번째 생성자에서'create'를 호출 할 필요가 없습니다. 또는'create()'자체가 깨 졌거나 무의미한 것이기 때문에 대안적인 수정이 _that_을 변경하는 것일 수도 있습니다. –

+0

@MooingDuck 작성한대로 동의합니다. OP가'create()' "family"에 기능을 추가하고 기본 ctor가 왜 그것을 선택하지 않는지 궁금해하는 경우, 그녀는 그것을 되돌릴 수 있다고 생각합니다. 나는 그것이 OP에 중요하게 보였기 때문에 그것을 지켰다. 그것을 변경하고 이니셜 라이저 목록을 사용하지 않는다면, 멤버 멤버가없는 객체에서 호출되는 멤버 함수 (또는 그와 관련된 다른 함수)에 대한 팬이 아닙니다. 나는 누군가가 그것들에 균열이 있기 전에 초기화 된 것을 좋아한다. (그러나 당신은 분명히 옳았습니다. – WhozCraig

+0

Thanks WhozCraig & SB. 나는이 책을 읽고 있었고 그 소스 코드는 초기화 프로그램 목록을 포함하지 않았기 때문에 inital이 문제라고 생각하지 않았다. – Emcy

관련 문제