1

我们在课堂上使用 pimpl 成语。pimpl 结构在包含 pimpl 指针的类中声明,如下所示:

struct MyClassImpl;
friend struct MyClassImpl;
boost::scoped_ptr<MyClassImpl> m_Impl;

pimpl 的实现在一个名为 MyClassImpl.cpp 的单独文件中,例如:

    struct MyClass::MyClassImpl
        {
            QString m_Name;                             
            int m_Type;                                 
            double m_Frequency;                         
            int m_DefaultSize;                          
            QVariant m_DefaultValue;
                 boost::shared_ptr<SomeOtherClass> m_SomeOtherClass;                    

            ~MyClassImpl()
            {
            }
        };

在包含 pimpl 指针的类的构造函数中,我将在成员变量初始化列表中具有类似

m_Impl(new MyClassImpl())

现在,我们在源代码中启用了内存泄漏检测,如下所示:

// Memory leaks detection in Visual Studio
#if defined (_WIN32) && defined (_DEBUG)
#   define _CRTDBG_MAP_ALLOC
#   include <crtdbg.h>
#   define new new(_NORMAL_BLOCK ,__FILE__, __LINE__) 
#endif

我发现当程序退出时,MyClassImpl() struct m_Impl(new MyClassImpl()) 会报告内存泄漏:

..\..\src\MyClass.cpp(29) : {290222} normal block at 0x0B9664E0, 48 bytes long.
 Data: <X l V         Y@> 58 1C 6C 03 56 00 00 00 00 00 00 00 00 00 59 40 

我不明白为什么因为 m_Impl 是 boost::scoped_ptr 并且 QString、QVariant 和 shared_ptr 都是托管的。有任何想法吗?

4

2 回答 2

1

也许 MyClass 的实例在没有被正确删除的情况下被释放?例如,如果使用placement new 将它们分配到某个地方,那么它们不会被报告为单独泄漏,但它们也不会在释放内存时自动销毁。

于 2011-03-17T15:09:30.447 回答
1

它看起来确实应该工作..

我觉得奇怪的是泄漏的大小,只有 48 个字节。

我得出的结论是MyClassImpl结构已释放,但其中的某些内容并未释放。如果整个结构泄漏,泄漏将比 48 字节大得多。

但是,我仍然找不到该代码的错误。

获取 Visual Leak Detector 以增强您的调试,它是免费的。

http://vld.codeplex.com/

于 2011-03-18T08:52:21.820 回答