Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/141.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 为什么运算符删除重载不';t调用delete时调用无限递归调用_C++_Delete Operator - Fatal编程技术网

C++ 为什么运算符删除重载不';t调用delete时调用无限递归调用

C++ 为什么运算符删除重载不';t调用delete时调用无限递归调用,c++,delete-operator,C++,Delete Operator,调用运算符new的本地重载会由于无限递归调用而导致堆栈溢出,但当运算符delete的本地重载发生相同情况时,为什么会调用全局运算符delete(从而避免堆栈崩溃)。 简单的代码是这样的- class A { public: void * operator new(size_t n) { //return new A();calls local overloaded version and stack overflows return ::new A();

调用运算符new的本地重载会由于无限递归调用而导致堆栈溢出,但当运算符delete的本地重载发生相同情况时,为什么会调用全局运算符delete(从而避免堆栈崩溃)。 简单的代码是这样的-

class A {
public:
    void * operator new(size_t n) {
        //return new A();calls local overloaded version and stack overflows
        return ::new A();
    }

    void operator delete(void* p)
    {
        delete(p);//why its calling global version?
        //::delete(p);//calls global version
    }
};

int main()
{
    A *a = new A();
    delete(a); 
}

我的问题是,为什么从重载运算符delete中删除不会调用自身,而是调用全局运算符delete?

我试图将我的评论总结到答案中

delete
是一个关键字,不是函数或运算符。因此,它的行为与函数不同

编写
delete p
时,编译器不会像查找函数那样执行重载查找。当编译器遇到表达式
delete p
时,它会在可用重载
operator delete
之间对指针类型
p
执行查找。如果
p
是指向类的指针,并且存在特定于类的重载,则调用
p->operator delete(some_ptr)
。否则,编译器将在作用域
void运算符delete(void*)
之间执行查找

回到你的例子

A *a = new A();
delete(a);  // a is pointer to class, calls a->operator delete(a);

void A::operator delete(void* p) {
  delete(p);  // p is pointer to void, calls ::operator delete(p);
}
如果您调用
操作员删除(a)
,它就像一个函数调用,
a::operator delete(void*)未被调用

如果您调用
操作符delete(p)
A::operator delete(void*p)的内部,得到无限递归


如果调用
delete static\u cast(p)
A::operator delete(void*p)的内部,您再次得到无限递归。

那么,您的意思是new和delete w.r.t之间的差异。无限递归只取决于参数类型(因为运算符delete需要处理void*或A*)?