Сопоставление объявлений
Любые два объявления функции с одинаковым именем в одной области видимости могут ссылаться на одну функцию или на две разные перегруженные функции. Если списки аргументов в объявлениях содержат аргументы эквивалентных типов (как описано в предыдущем разделе), эти объявления относятся к одной и той же функции. В противном случае они ссылаются на две различные функции, которые выбираются с использованием перегрузки.
Область видимости класса строго соблюдается; поэтому функция, объявленная в базовом классе, не находится в той же области видимости, что и функция, объявленная в производном классе. Если функция в производном классе объявлена с тем же именем, что и функция в базовом классе, функция производного класса скрывает функцию базового класса, а не вызывает перегрузку.
Область видимости блока строго соблюдается; поэтому функция, объявленная в области видимости файла, не находится в той же области видимости, что и функция, объявленная локально. Если локально объявленная функция имеет то же имя, что и функция, объявленная в области файла, локально объявленная функция скрывает функцию области файла, не вызывая перегрузки. Например:
// declaration_matching1.cpp
// compile with: /EHsc
#include <iostream>
using namespace std;
void func( int i )
{
cout << "Called file-scoped func : " << i << endl;
}
void func( char *sz )
{
cout << "Called locally declared func : " << sz << endl;
}
int main()
{
// Declare func local to main.
extern void func( char *sz );
func( 3 ); // C2664 Error. func( int ) is hidden.
func( "s" );
}
В предыдущем коде показаны два определения функции func. Определение, которое принимает аргумент типа char *, является локальным для функции main из-за оператора extern. Поэтому определение, которое принимает аргумент типа int, скрыто, и первый вызов функции func завершается ошибкой.
В случае перегруженных функций-членов различным версиям функции могут предоставляться разные права доступа. Они по-прежнему считаются находящимися в области видимости включающего класса и, таким образом, являются перегруженными функциями. Рассмотрим следующий код, в котором функция-член Deposit перегружена; одна версия является открытой, вторая — закрытой.
Целью кода в примере является предоставление класса Account, в котором для внесения средств требуется правильный пароль. Для этого используется перегрузка.
Обратите внимание, что при вызове функции Deposit в операторе Account::Deposit вызывается закрытая функция-член. Это правильный вызов, поскольку функция Account::Deposit является функцией-членом и, следовательно, имеет доступ к закрытым членам класса.
// declaration_matching2.cpp
class Account
{
public:
Account()
{
}
double Deposit( double dAmount, char *szPassword );
private:
double Deposit( double dAmount )
{
return 0.0;
}
int Validate( char *szPassword )
{
return 0;
}
};
int main()
{
// Allocate a new object of type Account.
Account *pAcct = new Account;
// Deposit $57.22. Error: calls a private function.
// pAcct->Deposit( 57.22 );
// Deposit $57.22 and supply a password. OK: calls a
// public function.
pAcct->Deposit( 52.77, "pswd" );
}
double Account::Deposit( double dAmount, char *szPassword )
{
if ( Validate( szPassword ) )
return Deposit( dAmount );
else
return 0.0;
}