对具有重载操作员>的类型进行就地销毁

In-place destruction on type with overloaded operator->

本文关键字:类型 重载 操作员 gt      更新时间:2023-10-16

假设某类型Foo有一个重载的operator->返回一个Bar*:

struct Foo
{
    Bar* operator->();
};

如果我想从Foo类中就地销毁返回的Bar实例,我可以写下面的代码吗?

this->~Bar();

g++不喜欢这样的代码。如果我这样写,它可以工作:

(*this)->~Bar();

"递归转发规则"在这种情况下不适用吗?为什么不呢?

链接->的规则,见于标准的13.5.6 [over.ref]:

对于类型为T的类对象x,如果T::operator->()存在并且操作符被重载解析机制(13.3)选为最佳匹配函数,则表达式x->m被解释为(x.operator->())->m

由于this是一个指针,而不是一个类对象,所以它不适用

相反,这个规则在5.2.5 ([expr.ref])是适用的:

对于第二个选项(箭头),第一个表达式应该有指向完整类类型的指针。表达式E1->E2被转换成等价形式(*(E1)).E2;5.2.5的剩余部分将只处理第一个选项(点)。

因为this是指针,不是引用,而->是指针,所以没有返回值来进行转发。考虑同样

shared_ptr<std::string>* ptr = // some init
ptr->push_back('0'); // error

this是指向Foo类型对象的指针。您覆盖了对象的操作符->,而不是指针。

this->~Bar()

尝试调用Foo中的~Bar()方法。

(*this)->~Bar()

工作是因为调用了对象的->操作符。