在运算符的情况下C ++ const转换

时间:2014-03-20 23:46:36

标签: c++ g++

请考虑以下代码:

struct A {
    void operator++() const {}
};

void operator++(const A&) {}


int main () {
    const A ca;
    ++ca; // g++ Error (as expected): ambiguous overload for ‘operator++’

    A a;
    ++a; // g++ Warning: "ISO C++ says that these are ambiguous,
         // even though the worst conversion for the first is better
         // than the worst conversion for the second"
         // candidate 1: void operator++(const A&)
         // candidate 2: void A::operator++() const
}

为什么g ++只在++a上发出警告而不是错误?换句话说,非成员函数如何比成员函数更合适?

谢谢!

2 个答案:

答案 0 :(得分:2)

如果我猜测,成员函数会在初始化A *时导致从A const *this的指针限定转换,而非成员绑定A const &引用到非const对象,根本不是转换,但在重载解析期间仅仅是非首选的情况。

当从参数类型引导到相应参数类型的路径涉及不同类型的转换时,会出现该消息。该标准拒绝将苹果与橙子进行比较,例如指针限定与参考绑定或整体提升与转换运算符,但GCC愿意。

答案 1 :(得分:1)

在c ++中,您可以为 const 而不是const 分隔方法(和运算符),当您不这样做时,编译器可以搜索 “最合适” const const 的最佳选择是 const

看一下这个例子:

struct S{
  void f(){cout<<"f";}
  void f()const{cout<<"f-const";}
};

int main(){
   const S sc;
   S s;
   s.f();
   sc.f();
   return 0;
}

第一次打印的输出为“f” 但对于第二个,它将是“f-const”

如果我从结构中删除 not const 方法,我将获得两个对象的相同输出。这是因为该函数称为“最适合”,因为它可以将“constiness”添加到非const对象。 (不能删除const方法,因为它根本不适合......)

在您的代码中没有明确的运算符 not const 所以当它找到“最适合”时,它可以从选项,并采取看起来最好的。你有一个警告,因为有两个适合,但它仍然选择其中之一,我不知道为什么一个看起来比另一个更好... 但是对于 const 它有两个显式函数,编译器无法选择何时有显式方法!这就是你出错的原因。

如果你想要相同的行为,还要添加 explicit not const 运算符,如下所示:

struct A {
    void operator++() const {}
    void operator++(){};
};

void operator++(const A&) {}
void operator++(A&) {}

现在你们两个都会得到同样的错误。