台词:
Var k = z + x*y;
电话
operator*
,它返回
Var
临时的,然后用于
r
论证
operator+
,其中
pair
k
子项包括指向临时
有
已经,但它不再存在。
Var xy = x * y;
xy.set_character('*');
Var k = z + xy;
k.set_character('k');
…您的程序使用它生成:
k = 37
âk/âx = 6
âk/ây = 5
âk/âz = 1
按价值
.
作为发现这些错误的一般提示。。。当您的程序似乎在做一些无法解释的事情(和/或崩溃)时,请尝试在内存错误检测器下运行它,如
valgrind
==22137== Invalid read of size 8
==22137== at 0x1090EA: Var::gradient(Var*) const (in /home/median/so/deriv)
==22137== by 0x109109: Var::gradient(Var*) const (in /home/median/so/deriv)
==22137== by 0x108E12: main (in /home/median/so/deriv)
==22137== Address 0x5b82cd0 is 0 bytes inside a block of size 32 free'd
==22137== at 0x4C3123B: operator delete(void*) (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==22137== by 0x109FC1: __gnu_cxx::new_allocator<std::pair<double, Var const*> >::deallocate(std::pair<double, Var const*>*, unsigned long) (in /home/median/so/deriv)
==22137== by 0x109CDD: std::allocator_traits<std::allocator<std::pair<double, Var const*> > >::deallocate(std::allocator<std::pair<double, Var const*> >&, std::pair<double, Var const*>*, unsigned long) (in /home/median/so/deriv)
==22137== by 0x109963: std::_Vector_base<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > >::_M_deallocate(std::pair<double, Var const*>*, unsigned long) (in /home/median/so/deriv)
==22137== by 0x1097BC: std::_Vector_base<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > >::~_Vector_base() (in /home/median/so/deriv)
==22137== by 0x1095EA: std::vector<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > >::~vector() (in /home/median/so/deriv)
==22137== by 0x109161: Var::~Var() (in /home/median/so/deriv)
==22137== by 0x108D95: main (in /home/median/so/deriv)
==22137== Block was alloc'd at
==22137== at 0x4C3017F: operator new(unsigned long) (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==22137== by 0x10A153: __gnu_cxx::new_allocator<std::pair<double, Var const*> >::allocate(unsigned long, void const*) (in /home/median/so/deriv)
==22137== by 0x10A060: std::allocator_traits<std::allocator<std::pair<double, Var const*> > >::allocate(std::allocator<std::pair<double, Var const*> >&, unsigned long) (in /home/median/so/deriv)
==22137== by 0x109F03: std::_Vector_base<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > >::_M_allocate(unsigned long) (in /home/median/so/deriv)
==22137== by 0x109A8D: void std::vector<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > >::_M_realloc_insert<std::pair<double, Var const*> >(__gnu_cxx::__normal_iterator<std::pair<double, Var const*>*, std::vector<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > > >, std::pair<double, Var const*>&&) (in /home/median/so/deriv)
==22137== by 0x1098CF: void std::vector<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > >::emplace_back<std::pair<double, Var const*> >(std::pair<double, Var const*>&&) (in /home/median/so/deriv)
==22137== by 0x10973F: std::vector<std::pair<double, Var const*>, std::allocator<std::pair<double, Var const*> > >::push_back(std::pair<double, Var const*>&&) (in /home/median/so/deriv)
==22137== by 0x109520: operator*(Var const&, Var const&) (in /home/median/so/deriv)
==22137== by 0x108D6F: main (in /home/median/so/deriv)
另一种捕获方法是在析构函数中添加日志记录,以便知道日志记录中提到的对象地址何时不再有效。