int res = operator+( si, iobj ); // синтаксис вызова функции

то применяется процедура разрешения перегрузки для функций в пространстве имен (см. раздел 15.10). Если же использован синтаксис вызова функции-члена:

// синтаксис вызова функции-члена

int res = si.operator+( iobj );

то работает соответствующая процедура для функций-членов (см. раздел 15.11).

<p>15.12.1. Операторные функции-кандидаты</p>

Операторная функция является кандидатом, если она имеет то же имя, что и вызванная. При использовании следующего оператора сложения

SmallInt si(98);

int iobj = 65;

int res = si + iobj;

операторной функцией-кандидатом является operator+. Какие объявления operator+ принимаются во внимание?

* Потенциально в случае применения операторного синтаксиса с операндами, имеющими тип класса, строится пять множеств кандидатов. Первые три – те же, что и при вызове обычных функций с аргументами типа класса: множество операторов, видимых в точке вызова. Объявления функции operator+(), видимые в точке использования оператора, являются кандидатами. Например, operator+(), объявленный в глобальной области видимости, – кандидат в случае применения operator+() внутри main():

SmallInt operator+ ( const SmallInt &, const SmallInt & );

int main() {

SmallInt si(98);

int iobj = 65;

int res = si + iobj; // ::operator+() - функция-кандидат

}

* множество операторов, объявленных в пространстве имен, в котором определен тип операнда. Если операнд имеет тип класса и этот тип объявлен в пользовательском пространстве имен, то операторные функции, объявленные в том же пространстве и имеющие то же имя, что и использованный оператор, считаются кандидатами:

namespace NS {

class SmallInt { /* ... */ };

SmallInt operator+ ( const SmallInt&, double );

}

int main() {

// si имеет тип SmallInt:

// этот класс объявлен в пространстве имен NS

NS::SmallInt si(15);

// NS::operator+() - функция-кандидат

int res = si + 566;

return 0;

}

* Операнд si имеет тип класса SmallInt, объявленного в пространстве имен NS. Поэтому перегруженный operator+(const SmallInt, double), объявленный в том же пространстве, добавляется к множеству кандидатов; множество операторов, объявленных друзьями классов, к которым принадлежат операнды. Если операнд принадлежит к типу класса и в определении этого класса есть одноименные применяемому оператору функции-друзья, то они добавляются к множеству кандидатов:

namespace NS {

class SmallInt {

friend SmallInt operator+( const SmallInt&, int )

{ /* ... */ }

};

}

int main() {

NS::SmallInt si(15);

// функция-друг operator+() - кандидат

int res = si + 566;

return 0;

}

* Операнд si имеет тип SmallInt. Операторная функция operator+(const SmallInt&, int), являющаяся другом этого класса, – член пространства имен NS, хотя непосредственно в этом пространстве она не объявлена. При обычном поиске в NS эта операторная функция не будет найдена. Однако при использовании operator+() с аргументом типа SmallInt функции-друзья, объявленные в области видимости этого класса, включаются в рассмотрение и добавляются к множеству кандидатов. Эти три множества операторных функций-кандидатов формируются точно так же, как и для вызовов обычных функций с аргументами типа класса. Однако при использовании операторного синтаксиса строятся еще два множества: множество операторов-членов, объявленных в классе левого операнда. Если такой операнд оператора operator+() имеет тип класса, то в множество функций-кандидатов включаются объявления operator+(), являющиеся членами этого класса:

class myFloat {

myFloat( double );

};

class SmallInt {

public:

SmallInt( int );

SmallInt operator+ ( const myFloat & );

};

int main() {

SmallInt si(15);

int res = si + 5.66; // оператор-член operator+() - кандидат

}

* Оператор-член SmallInt::operator+(const myFloat &), определенный в SmallInt, включается в множество функций-кандидатов для разрешения вызова operator+() в main(); множество встроенных операторов. Учитывая типы, которые можно использовать со встроенным operator+(), кандидатами являются также:

Перейти на страницу:

Похожие книги