C++必知必会之(26)操作符函数查找

1、有时看上去好像一个成员操作符函数重载了一个非成员的操作符,其实并非如此。

这不是重载,只是不同的查找算法。

考虑如下类,它以成员函数的形式重载了一个操作符函数:

class X {

    public:

       X  operator %( const X & ) const;        //二元取余操作符

       X  memFunc1( const X & );

       void memFunc2( );

       //....

};

可以采用中缀或函数调用语法来调用这个重载的操作符函数:

X a, b, c;

a = b % c;     //采用中缀语法调用成员操作符%

a = b.operator % ( c) ;       //成员函数调用语法

a = b.memFunc1( c);             //另一个成员函数调用


当我们使用函数调用语法时,应用的是普通的查找规则,也就是说,对b.operator %(c)调用的处理方式与memFunc1的相同。

然而,对重载操作符的中缀调用的处理机制则与此不同:

X operator %( const X &, int );      //非成员操作符

//.....

void X::memFunc2( )   {

       *this % 12;   //调用非成员操作符%

       operaotr %( *this, 12 );         //错误,实参太多

}

对于中缀操作符调用来说,编译器不仅会考虑成员操作符,也会考虑非成员操作符,

因此第一个对operator%的中缀调用,将会匹配非成员的那一个。

不是一个重载的例子,而是编译器在两个不同的地方查找候选函数。

第二个对operator%的非中缀调用遵循标准的函数查找规则,因而匹配那个成员函数。

这里我们遇到一个错误,因为我们试图将三个实参传递给一个二元函数(记住,对成员函数的调用存在一个隐式的实参this)。


实际上,对重载操作符的中缀调用执行了一个退化形式的ADL,即当确定将哪些函数纳入重载解析考虑范围时,中缀操作符中左参数的类(可能只有一个左参数,而没有右参数)的作用域和全局作用域都被考虑在内。

ADL则将这个过程扩展到被操作符实参所带入的其他名字空间中候选操作符函数。

注意这并不是重载。

重载是一个和函数声明有关的静态属性,而ADL和中缀操作符函数查找都属于提供给函数调用的实参的属性。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值