- 2
- 0
- 约4.2千字
- 约 11页
- 2018-08-11 发布于福建
- 举报
C中类和继承对重载影响
C中类和继承对重载影响
摘要:函数重载的解析是C++编译时最复杂的问题之一,当函数重载与类和继承等问题结合在一起时就显得更为复杂。
关键词:重载;继承;虚函数
一、重载和重载解析
(一)函数的重载
函数重载是C++实现的重要特性之一,它指是指同一个函数名可以对应着多个函数的实现,这种实现依赖于函数参数属性的差异。重载只有函数在同一个域里声明时才能产生。C++标准区分五种域:名字空间域、类域、函数域、原型域、基本块域。对于函数域和原型域不会产生函数重载的问题。using关键字可以使在不同的名字空间里定义的函数构成重载。在考虑域对函数重载照成的影响时,也要注意全局和局部之间产生的函数隐藏问题。
(二)函数重载的解析
函数重载的解析有三个步骤,这三步严格按照顺序进行。解析骤如下:
第一步是选取候选函数, 候选函数与被调用的函数具有相同的名字,并且在调用点是可见的,同时确定调用函数实参的属性。
第二步是选择可行函数, 可行函数的参数表或者与调用中的实参数目相同, 或者有更多的参数, 在后一种情况下, 额外的参数会被给出缺省参数; 并且对于每个实参, 都存在到函数列表中相应的参数类型之间转换的函数。
第三步是选择最佳可行函数, 最佳可行函数是具有与实参类型匹配最好的参数的可行函数。在最佳可行函数的选择中,从函数实参类型到相应可行函数参数所用的转化都要划分等级,根据等级的划分(ranked),最后选出最佳可行函数
对于简单的C++程序来说,选取候选函数只要根据同名可见的原则就能产生。但是对于可行函数和最佳可行函数的选取时,参数类型和个数的匹配,类型转化等级的划分都是十分复杂的,在很多教材上也有详细的论述,这里不再累述。
类和继承也是C++的重要特性,也是C++里比较复杂的部分,值得关注的是它们和函数重载结合到一起时会变的更为复杂,其中对于候选函数选取有影响显得尤为重要,下面进行详细的讨论。
二、类与函数重载
(一)成员函数的重载
类对于函数重载的影响,主要是由类域产生的。属于同一个类的成员函数属于同一个域,因此在重载解析的第一步所有的同名函数都被列入候选函数。而对于不在同一个类域中声明的函数,如果我们希望它加入候选函数,可以声明成友元。
(二)继承对重载的影响
在C++中继承是构成面向对象程序设计思想的重要概念之一。父类的函数可以被继承到子类中,子类中没有同名函数时,被继承的函数能够保持重载的特性,但是当子类中出现同名函数时,子类的函数会隐藏父类的函数,例如:
class Basic
{public:
void fun(){}
void fun(int i){}
};
class Derive :public Basic
{public:
void fun(int i,int j){}
};
int main()
{ Derive d;
d.fun(2,4);
}
在本例中只能调用派生类中的函数fun( ),企图通过重载调用基类的函数fun( )则不能成功,因为在派生类中基类的同名函数被隐藏,即使它们的参数不同。若想实现重载可以通过两种方式:
1) 在派生类中重新定义,例如:
class Derive :public Basic
{public:
void fun(){}
void fun(int i){}
void fun(int i,int j){}
};
2)使用using关键字,通过using关键字的使用可以使被隐藏的基类中的函数fun()在派生类中可见。例如在派生类中声明using Basic::fun。
(三)多重继承对重载的影响
在多重继承的派生类中建立候选成员函数集时,同名的成员函数如果是由多个基类继承来的会产生错误,例如
class Basic1
{public:
print(int i) { }
};
class Basic2
{public:
print(int i,int j) { }
};
class Derive: public Basic1, public Basic2{...};
void main()
{ Derive d;
d.print( 1 );
}
当在Derive的域中查找成员函数print()的声明时,找到了Basic1::print()和Basic2::print()。 因为它们不是在同一个基类中被找到的,即使这两个print
原创力文档

文档评论(0)