为什么在这段代码中(这只是工作代码而不是完全异常安全)我收到一个断言错误:
HEAP_CORRUPTION_DETECTED ...
class Allocator
{
public:
explicit Allocator()
{
std::cout << "Allocator()" << '\n';
}
virtual ~Allocator()
{
std::cout << "~Allocator()" << '\n';
}
template<class T>
T* Allocate(const std::size_t count)
{
return static_cast<T*>(::operator new(count));
}
/*[nothrow]*/
template<class T>
void Construct(void* where_, const T& what)
{
new (where_) T(what);
}
template<class T>
void Destruct(T* where_)
{
where_->~T();
}
template<class FwdIter>
void Destruct(FwdIter first, FwdIter last)
{
while (first != last)
{
this->Destruct(&*first);
++first;
}
}
template<class T>
void Deallocate(T* where_)
{
::operator delete(where_);
}
};
template<class T>
class ToyImplementation
{
private:
public:
typedef T value_type;
T* data_;///move to private
std::size_t size_;
std::size_t capacity_;
explicit ToyImplementation(Allocator& alloc, const std::size_t count):data_(alloc.Allocate<value_type>(count)),size_(0),capacity_(count)
{
std::cout << "ToyImplementation()" << '\n';
//throw std::exception();
}
~ToyImplementation()
{
std::cout << "~ToyImplementation()" << '\n';
}
};
template<class T>
class ToyA
{
private:
ToyImplementation<T>* implementation_;
typedef ToyImplementation<T> value_type;
Allocator alloc_;
public:
explicit ToyA(const std::size_t count = 0): implementation_(alloc_.Allocate<value_type>(sizeof(value_type)))
{
alloc_.Construct(implementation_, value_type(alloc_,count));
alloc_.Deallocate(implementation_);//<<--------HERE ERROR IS TRIGGERED
std::cout << "Toy()" << '\n';
}
~ToyA()
{
std::cout << "~Toy()" << '\n';
}
};
int _tmain(int argc, _TCHAR* argv[])
{
ToyA<int> t(10);
return 0;
}
七行是一行导致错误。线被标记为&lt;&--------这里错误被触发了 谢谢。
答案 0 :(得分:5)
您的堆已损坏,因为您的分配不正确。即,考虑一下:
template<class T>
T* Allocate(const std::size_t count)
{
return static_cast<T*>(::operator new(count));
}
如果count
为1,则得到一个字节。 (然后你尝试在那个记忆中构造一个大小超过1的物体......繁荣。)
你可能想要:
template<class T>
T* Allocate(const std::size_t count)
{
return static_cast<T*>(::operator new(sizeof(T) * count));
}
注意你的功能设计有点不正统。分配和释放函数应该严格分配和解除分配(没有强制转换!),如下所示:
template<class T>
void* Allocate(const std::size_t count)
{
return ::operator new(sizeof(T) * count);
}
void Deallocate(void* where_)
{
::operator delete(where_);
}
你的构造和销毁函数应该是构造和返回一个对象并破坏一个对象的函数:
template<class T>
T* Construct(void* where_, const T& what)
{
return new (where_) T(what);
}