虚函数在笔试中的题型

下面总结了一些虚函数在笔试中的题型

  1. 构造函数可以调用虚函数吗?语法上通过吗?语义上可以通过吗?
    可以,语法可以通过,但是不能实现多态,其语义是无法通过的。根据C++类初始化方式的定义,派生类在初始化时会调用父类的构造函数,但是若在调用父类的构造函数中出现了虚函数,是不会呈现多态的,因为此时派生类还没有完成初始化,所以是不能呈现多态的。如果在基类的构造中调用虚函数,如果可以的话就是调用一个还没有被初始化的对象,那是很危险的,所以C++中是不可以在构造父类对象部分的时候调用子类的虚函数实现。但是不是说你不可以那么写程序,你这么写,编译器也不会报错。

  2. 构造函数可以调用虚函数吗?语法上通过吗?语义上可以通过吗?

    可以。语法上可以通过。但是非常危险,不推荐使用。在析构函数中也不要调用虚函数。在析构的时候会首先调用子类的析构函数,析构掉对象中的子类部分,然后在调用基类的析构函数析构基类部分,如果在基类的析构函数里面调用虚函数,会导致其调用已经析构了的子类对象里面的函数,这是非常危险的

  3. 构造、析构函数可以是虚函数吗?

    构造函数不可以是虚函数,因为构造时,对象还是一片未定型的处女地(感觉钱能老师文笔好叼),只有在完成构造完成后,对象才能成为一个名副其实的对象。

    析构函数可以是虚函数,并且通常申明为虚函数。在类的继承中,如果有基类的指针指向派生类的对象,若基类的构造函数不是虚函数,则派生类的那部分无法完成析构,所以最好将基类的析构函数申明为虚函数,在删除基类指针的时候,首先会调用子类的析构函数。

    同时还包括以下几个问题:

    1. 静态成员函数可以是虚函数吗?

      静态成员函数不可以是虚函数,因为静态成员函数不接受对象的捆绑调用。不能捆绑调用也就失去了多态的必要条件,因为多态就是在运行时根据实际的对象,调用其相应得虚函数(滞后绑定),所以静态成员函数不可以是虚函数。

    2. 内联函数可以是虚函数吗?

      内联函数不可以是虚函数,因为虚函数是滞后绑定,而内联函数是不能在运行中动态的确定其位置。即使虚函数在类的内部定义,编译器编译时仍然将她视为非内联。

      最后强调一句,只有类的成员函数才能申明为虚函数。

1

</pre><pre class="cpp" name="code">#include<iostream>

using namespace std;

class B{

public:

       virtualB* _fun(){

              cout<< "In B" << endl;

              returnthis;

       }

};

class D :public B{

public:

       D*_fun(){

              cout<< "In D" << endl;

              returnthis;

       }

};

void fun(B *b){

       B*bb;

       bb=b->_fun();

 

}

int main(){

       fun(&B());

       fun(&D());

       return0;

}


运行结果:

分析,在****之前是继承关系中的构造函数调用,在****之后是继承关系中的析构函数调用,从中可以得出,析构、构造函数都可以调用虚函数,但是析构函数中的虚函数是不能体现多态的,比如结果第一条输出(Base:fun)就是在基类中的。

 

关于虚函数的滞后绑定其余的不用多解释,下面介绍一个特例。

关于虚函数的滞后绑定,必须要求父类、子类的虚函数,返回类型、名称、行参一模一样。但是有个例外,那就是允许子类、父类的虚函数的返回值是各自的对象指针。

如下所示:

#include<iostream>
using namespace std;
class B{
public:
	virtual B* _fun(){
		cout << "In B" << endl;
		return this;
	}
};
class D :public B{
public:
	D* _fun(){
		cout << "In D" << endl;
		return this;
	}
};
void fun(B *b){
	B *bb;
	bb=b->_fun();

}
int main(){
	fun(&B());
	fun(&D());
	return 0;
}

这个例外是可以理解的。因为父类、子类的虚函数返回各自的对象指针,更自然,更符合函数调用的一些习惯,但是只能这样书写才符合规范。在一般函数定义中,若函数至今仅仅是函数的返回值不同,则编译器会分不清调用哪个函数而报错,比如以下两个函数在一个源文件中会报错。

Void f(int)

Int f(int)

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值