继承类内存泄漏

时间:2015-11-21 16:40:26

标签: c++ memory-leaks

我在我正在研究的项目中创建了这个模式:

struct Item {};
struct Base {
    struct Result {
        std::shared_ptr<Base> base_ptr;
        Result(Base * base) : base_ptr(base) {}
    };
    virtual Base::Result update() const = 0;
};
struct Sub : public Base {
    const std::vector<Item> items;
    Sub(std::vector<Item> items) : items(items) {}
    Base::Result update() const override {
        return {new Sub{items}};
    }
};
int main() {
    std::vector<Item> items{Item{}};
    auto base = std::shared_ptr<Base>{new Sub{items}};
    auto result = base->update();
}

根据valgrind导致向量泄漏:

==21663== 1 bytes in 1 blocks are definitely lost in loss record 1 of 2
==21663==    at 0x4C29158: operator new(unsigned long) (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==21663==    by 0x401DC5: __gnu_cxx::new_allocator<Item>::allocate(unsigned long, void const*) (in /home/user/code/test_leak/a.out)
==21663==    by 0x401C64: std::allocator_traits<std::allocator<Item> >::allocate(std::allocator<Item>&, unsigned long) (in /home/user/code/test_leak/a.out)
==21663==    by 0x4019D7: std::_Vector_base<Item, std::allocator<Item> >::_M_allocate(unsigned long) (in /home/user/code/test_leak/a.out)
==21663==    by 0x401890: std::_Vector_base<Item, std::allocator<Item> >::_M_create_storage(unsigned long) (in /home/user/code/test_leak/a.out)
==21663==    by 0x401428: std::_Vector_base<Item, std::allocator<Item> >::_Vector_base(unsigned long, std::allocator<Item> const&) (in /home/user/code/test_leak/a.out)
==21663==    by 0x401044: std::vector<Item, std::allocator<Item> >::vector(std::vector<Item, std::allocator<Item> > const&) (in /home/user/code/test_leak/a.out)
==21663==    by 0x400EAA: Sub::Sub(std::vector<Item, std::allocator<Item> >) (in /home/user/code/test_leak/a.out)
==21663==    by 0x400F4B: Sub::update() const (in /home/user/code/test_leak/a.out)
==21663==    by 0x400D02: main (in /home/user/code/test_leak/a.out)
==21663== 
==21663== LEAK SUMMARY:
==21663==    definitely lost: 1 bytes in 1 blocks

如果代码被更改为返回shared_ptr而不是Base :: Result,则没有泄漏,但我需要返回多于shared_ptr以便将一些消息传递给接收者。

如果有一种传统模式可以更好地解决这个问题,那么我当然对此感兴趣。否则我想知道如何通过修改我当前的代码来修复泄漏。

1 个答案:

答案 0 :(得分:4)

您忘了在Base struct:

中定义虚拟析构函数
virtual ~Base() {}