以下C++代码是否相同?(在智能指针实现中)

ano*_*non 2 c++ templates pointers

代码1:

template<class T>
const PtrInterface<T>*
PtrInterface<T>::newRef() const {
  PtrInterface<T>* me = (PtrInterface<T>*) this;
  ++me->references_;
  //++this->references_;
  return this;
} 
Run Code Online (Sandbox Code Playgroud)

代码2:

template<class T>
const PtrInterface<T>*
PtrInterface<T>::newRef() const {
  //PtrInterface<T>* me = (PtrInterface<T>*) this;
  //++me->references_;
  ++this->references_;
  return this;
}
Run Code Online (Sandbox Code Playgroud)

是否有任何情况下这两个代码块会做不同的事情?谢谢!

GMa*_*ckG 7

是否有任何情况下这两个代码块会做不同的事情?

是的,当你在一个const方法.目前,具有me调用未定义行为的那个.原因如下:

如您所知,当您调用成员函数时,会有一个隐式this指针.该this指针是const当一个函数被标记const.以此为例:

struct foo
{
    void method1(void);
    void method2(void) const;

    int i;
};
Run Code Online (Sandbox Code Playgroud)

隐式地,编译器生成(顺便说一句,这是简化的):

void foo::method1(foo* this); 
void foo::method2(const foo* this) const;
Run Code Online (Sandbox Code Playgroud)

那么,这两个身体是一样的吗?

foo* me = (foo*)this;
me->i = 1;

// and

this->i = 1;
Run Code Online (Sandbox Code Playgroud)

答案取决于它,如前所述,它取决于const函数的性质.在非const功能中,它们是相同的:

void foo::method1(foo* this)
{
    foo* me = (foo*)this; // this cast is redundant
    me->i = 1;

    // ...

    this->i = 1;
}
Run Code Online (Sandbox Code Playgroud)

但在一个const功能:

void foo::method2(const foo* this) const
{
    foo* me = (foo*)this; // uh-oh! acts like const_cast
    me->i = 1; // modifying a const_cast'd variable is undefined behavior

    // ...

    this->i = 1; // wouldn't compile
}
Run Code Online (Sandbox Code Playgroud)

我们最终剥离了const.所以,不,他们并不总是一样的.这是C风格演员的危险:它会找到一种方法.顺便说一句,const抛弃本身并不是不确定的行为; 这是对所述变量的修改.

你的问题有一个棘手的问题:你的代码不应该编译.与上面的注释代码一样,在您的const方法中,您应该无法修改reference_.

这是不同的,如果reference_mutable,我猜它可能是(假设你给了我们可编译的代码.)在这种情况下,我不确定第一个样本是否导致未定义的行为,因为它是mutable在第一位.我不会抓住机会.