我如何为由unique_ptr管理的数组编写自定义删除器?

问题描述 投票:0回答:2

我正在尝试找到一种方法,用于为模板化的C ++类中由unique_ptr管理的C数组编写自定义删除器。我有意通过使删除器不执行任何操作来使类泄漏内存。在完整类中,一些构造函数分配内存,而有些则不分配-而是他们利用来自数据流的原始字节缓冲区中的内存。

这是我尝试过的:

template <class T> class Matrix
{
    private:
    int _size;
    std::unique_ptr<T[]> _array;

    public:
    Matrix(int size, void* data) : _size(size)
                                 , _array(NULL, [](T[]* p){})
    {
        _array.reset((T*)data);
    }
};

代码未编译,错误消息是:

In file included from /tmp/test/test/test.cpp:9:
/tmp/test/test/Matrix.h:22:55: error: expected ')'
                                 , _array(NULL, [](T[]* p){})
                                                      ^
/tmp/test/test/Matrix.h:22:51: note: to match this '('
                                 , _array(NULL, [](T[]* p){})
                                                  ^
1 error generated.
c++ destructor unique-ptr
2个回答
0
投票

首先,总是创建一个简单的设置来测试事物:

int main() {
    using T = int;

    std::unique_ptr<T[]> _array(NULL, [](T[]* p){});

    return 0;
}

现在就解决您的问题:

  • [T[]* p无效,应为T* p
  • 您作为删除者传递的lambda与用作默认删除者的std::default_delete<T>不匹配。因此,您必须写std::unique_ptr<T[],std::function<void(T*)>
  • [NULL可能被实现为整数类型,因此您应改用nullptr,否则gcc不会编译您的代码(因为c ++ 11,通常应改用nullptrNULL)。

因此将所有内容组合在一起:

int main() {
    using T = int;

    std::unique_ptr<T[],std::function<void(T[])>> _array(nullptr, [](T* p){});

    return 0;
}

0
投票

删除程序是std::unique_ptr的模板参数。默认情况下为std::default_delete,但您可以指定其他名称,例如

template <typename T>
struct NonDeleter
{
    void operator()(T*) { /* nothing */ }
};

template <typename T>
struct NonDeleter<T[]> : NonDeleter<T> {};

template <class T> class Matrix
{
    private:
    int _size;
    std::unique_ptr<T[], NonDeleter<T[]>> _array;

    public:
    Matrix(int size, void* data) : _size(size)
                                 , _array(data)
    {
    }
};
© www.soinside.com 2019 - 2024. All rights reserved.