问题描述
我想在我的项目中进行内存管理。我不想运算符全局新/删除,因此我实现一个简单的内存分配器。这是我的代码:
i want do memory management in my project. i do not want operator global new/delete so i implement a simple memory alloctor. this is my code:
class IAllocator
{
public:
void* Alloc( unsigned int size )
{
1. alloc memory.
2. trace alloc.
}
void Dealloc( void* ptr )
{
1. free memory.
2. erase trace info.
}
template< typename T >
void Destructor( T* ptr )
{
if ( ptr )
ptr->~T();
}
};
// macro for use easy.
# define MYNEW( T ) new ( g_Allocator->Alloc( sizeof( T ) ) ) T
# define MYDEL( ptr ) if (ptr) { g_Allocator->Destructor(ptr); g_Allocator->Dealloc(ptr); }
然后,我可以使用MYNEW来构造对象和$ MYDEL来销毁对象(擦除跟踪信息)。
Then, i can use MYNEW to construct object( also trace alloc info for check memory leak ), and MYDEL to destroy object( erase trace info ).
一切看起来很好...但是,当我尝试使用这种方法为多继承类,我发现一个非常严重的问题。看下我的测试代码:
Everything looks fine... but, when i try to use this method for multiple inheritance class, i found a very serious problem. look my test code below:
class A { ... };
Class B { ... };
Class C : public A, public B { ... };
C* pkC = MYNEW( C );
B* pkB = (B*)pkA;
MYDEL( pkB );
pkB和pkA的地址不相等。所以内存不会释放正确,并且alloc跟踪信息也不会擦除coorect ...哦...
the address of pkB and pkA does not equal. so the memory will not free correct, and the alloc trace info will not erase coorect too...oh...
有没有办法来解决这个问题? / p>
Is there any way to solve this problem?
推荐答案
如果 ptr
指向多态类的实例, c $ c> dynamic_cast< void *>(ptr)将产生一个指向 ptr
指向的最导出对象的指针。换句话说,这个动态转换产生一个指向分配地址的指针。
If ptr
points to an instance of a polymorphic class, dynamic_cast<void*>(ptr)
will result in a pointer to the most derived object pointed to by ptr
. In other words, this dynamic cast yields a pointer to the as-allocated address.
但是,使用 g_Allocator-> Dealloc(dynamic_cast< void *>(ptr))
是不可行的解决方案。问题是 dynamic_cast< void *>(ptr)
是非法的,如果 ptr
指向一个非类对象(例如,一个原语)或一个非多态类的实例。
However, using g_Allocator->Dealloc(dynamic_cast<void*>(ptr))
is not a viable solution. The problem is that dynamic_cast<void*>(ptr)
is illegal if ptr
points to a non-class object (e.g., a primitive) or to an instance of a non-polymorphic class.
你可以做的是使用SFINAE创建一个函数,到多态类,但使用静态转型为指向非类对象和非多态类的实例的指针。 Boost(现在是C ++ 11)提供 is_class< T>
和 is_polymorphic< T>
What you can do is use SFINAE to create a function that uses this dynamic cast for pointers to polymorphic classes but uses a static cast for pointers to non-class objects and instances of non-polymorphic classes. Boost (and now C++11) provides is_class<T>
and is_polymorphic<T>
type traits that will help in this regard.
示例:
template <typename T, bool is_poly>
struct GetAllocatedPointerHelper {
static void* cast (T* ptr) { return ptr; }
};
template <typename T>
struct GetAllocatedPointerHelper<T, true> {
static void* cast (T* ptr) { return dynamic_cast<void*>(ptr); }
};
template<typename T>
inline void*
get_allocated_pointer (T* ptr)
{
const bool is_poly = Boost::is_polymorphic<T>::value;
return GetAllocatedPointerHelper<T, is_poly>::cast(ptr);
}
这篇关于定制内存alloc和dealloc哪个多继承类的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!