探讨虚函数与纯虚函数的区别

2024-03-10 02:38
文章标签 函数 区别 探讨 纯虚

本文主要是介绍探讨虚函数与纯虚函数的区别,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

转载请注明t1234xy4原创:http://blog.csdn.net/t1234xy4/article/details/51191270
《C++ Primer》书上学习得到的基础:
纯虚函数:
1、纯虚函数只声明,没有定义。书写=0说明为纯虚函数。
2、含有纯虚函数的内,称为抽象基类,所谓抽象基类只负责定义接口,后续的其他类可以覆盖该接口,我们不能创建抽象基类的实例。
3、能够被覆盖。

普通虚函数:
1、声明为普通函数前加virtual,不仅要申明,而且必须定义。
2、能够被覆盖。(只有虚函数能够被覆盖)

测试虚函数与纯虚函数区别:
测试1、测试纯虚函数能不能有重名而函数个数不同的重载:
//virtualBase.hxx:

#include <string>
#include <iostream>
#pragma once
using namespace std;
class VirtualBase
{
public:VirtualBase(void);virtual void  helloword(string s)=0;virtual void helloword(string s1,string s2)=0;~VirtualBase(void);
};

virtualclass 继承了virtualBase

VirtualClass.hxx :

#pragma once
#include "virtualbase.h"
#include "VirtualBaseCopy.h"
class VirtualClass :public VirtualBase/*,public VirtualBaseCopy*/
{
public:VirtualClass(void);virtual void helloword(string s);virtual void helloword(string s1,string s2);~VirtualClass(void);
};

virtualclass.c

#include "StdAfx.h"
#include "VirtualClass.h"void VirtualClass::helloword(string s1,string s2)
{cout << "VirtualClass: hello ,"<<s1 <<","<<s2<<endl;
}
void VirtualClass::helloword(string s)
{cout << "virtualclass: hello,"<<s<<endl;
}

Main.c:

int _tmain(int argc, _TCHAR* argv[])
{**VirtualBase *base = new VirtualClass; //注意此处**string s = "jack";string s2 = "rose";base->helloword(s,s2);base->helloword(s);while (1){}return 0;
}

执行结果如下:
这里写图片描述
测试1结论:如果基类拥有重载纯虚函数接口,子类分别实例化后可用。也就是说,子类重写的两个函数分别覆盖了基类的两个函数。

测试2:如果基类VirtualBase中只有其中一个接口?,子类中是否可以出现同名的函数。
修改VirtualBase.hxx如下:

#include <string>
#include <iostream>
#pragma once
using namespace std;
class VirtualBase
{
public:VirtualBase(void);//virtual void  helloword(string s)=0;virtual void helloword(string s1,string s2)=0;~VirtualBase(void);
};
int _tmain(int argc, _TCHAR* argv[])
{**VirtualClass *base = new VirtualClass;**//注意此处string s = "jack";string s2 = "rose";base->helloword(s,s2);base->helloword(s);//cout<<base->add(2,3);while (1){}return 0;
}

结果:
这里写图片描述

修改为下面的后:

**VirtualBase *base = new VirtualClass;**//注意此处

编译不通过。
测试2结论:
1、编译不通过在情理之中,基类的指针开辟的空间结构不具有另一个函数的指针。
2、helloword(string s1,string s2)是VirtualClass的虚函数可行,运行没有问题。也就是说,子类可以出现与父类接口同名的函数。

虚函数是可以连续继承的。也就是说,一个函数在基类中为虚函数,那么在他的子子孙孙类中都是虚函数。

测试3: VirtualClass的子类还能否够继承他
我们添加类VirtualConcreate继承VirtualClass类,并重写虚函数helloword(string s):

void VirtualConcreate::helloword(string s)
{cout<<"concrete:hello,"<<s<<endl;
}

实例化如下:

**VirtualBase *base = new VirtualConcreate;**

结果如下:
这里写图片描述

测试3结论如下:
1、如果在VirtualConcrete类中,函数中重写了父类的虚函数,那么父类的虚函数将被覆盖掉;
2、子类中没有重写的父类函数,直接调用父类函数;

测试4:基类的接口,在其派生类中出现了与接口同名(函数个数不同或者参数不同)的虚函数是否一起被继承。
这里写图片描述
测试4结论:可以一起被继承。

测试总结:虚函数也可用重载,纯虚函数一样可以重载。,只有形参类型完全相同的虚函数才会被覆盖!!

测试5:普通成员函数与虚函数区别。
虚函数:
1、只有虚函数才能被覆盖(《C++ primer(第5版)》 538页)
2、虚函数是动态绑定

成员函数:
1、成员函数是静态绑定

这篇关于探讨虚函数与纯虚函数的区别的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/792752

相关文章

Oracle的to_date()函数详解

《Oracle的to_date()函数详解》Oracle的to_date()函数用于日期格式转换,需要注意Oracle中不区分大小写的MM和mm格式代码,应使用mi代替分钟,此外,Oracle还支持毫... 目录oracle的to_date()函数一.在使用Oracle的to_date函数来做日期转换二.日

结构体和联合体的区别及说明

《结构体和联合体的区别及说明》文章主要介绍了C语言中的结构体和联合体,结构体是一种自定义的复合数据类型,可以包含多个成员,每个成员可以是不同的数据类型,联合体是一种特殊的数据结构,可以在内存中共享同一... 目录结构体和联合体的区别1. 结构体(Struct)2. 联合体(Union)3. 联合体与结构体的

什么是 Ubuntu LTS?Ubuntu LTS和普通版本区别对比

《什么是UbuntuLTS?UbuntuLTS和普通版本区别对比》UbuntuLTS是Ubuntu操作系统的一个特殊版本,旨在提供更长时间的支持和稳定性,与常规的Ubuntu版本相比,LTS版... 如果你正打算安装 Ubuntu 系统,可能会被「LTS 版本」和「普通版本」给搞得一头雾水吧?尤其是对于刚入

python中json.dumps和json.dump区别

《python中json.dumps和json.dump区别》json.dumps将Python对象序列化为JSON字符串,json.dump直接将Python对象序列化写入文件,本文就来介绍一下两个... 目录1、json.dumps和json.dump的区别2、使用 json.dumps() 然后写入文

C++11的函数包装器std::function使用示例

《C++11的函数包装器std::function使用示例》C++11引入的std::function是最常用的函数包装器,它可以存储任何可调用对象并提供统一的调用接口,以下是关于函数包装器的详细讲解... 目录一、std::function 的基本用法1. 基本语法二、如何使用 std::function

hdu1171(母函数或多重背包)

题意:把物品分成两份,使得价值最接近 可以用背包,或者是母函数来解,母函数(1 + x^v+x^2v+.....+x^num*v)(1 + x^v+x^2v+.....+x^num*v)(1 + x^v+x^2v+.....+x^num*v) 其中指数为价值,每一项的数目为(该物品数+1)个 代码如下: #include<iostream>#include<algorithm>

native和static native区别

本文基于Hello JNI  如有疑惑,请看之前几篇文章。 native 与 static native java中 public native String helloJni();public native static String helloJniStatic();1212 JNI中 JNIEXPORT jstring JNICALL Java_com_test_g

C++操作符重载实例(独立函数)

C++操作符重载实例,我们把坐标值CVector的加法进行重载,计算c3=c1+c2时,也就是计算x3=x1+x2,y3=y1+y2,今天我们以独立函数的方式重载操作符+(加号),以下是C++代码: c1802.cpp源代码: D:\YcjWork\CppTour>vim c1802.cpp #include <iostream>using namespace std;/*** 以独立函数

函数式编程思想

我们经常会用到各种各样的编程思想,例如面向过程、面向对象。不过笔者在该博客简单介绍一下函数式编程思想. 如果对函数式编程思想进行概括,就是f(x) = na(x) , y=uf(x)…至于其他的编程思想,可能是y=a(x)+b(x)+c(x)…,也有可能是y=f(x)=f(x)/a + f(x)/b+f(x)/c… 面向过程的指令式编程 面向过程,简单理解就是y=a(x)+b(x)+c(x)

Android fill_parent、match_parent、wrap_content三者的作用及区别

这三个属性都是用来适应视图的水平或者垂直大小,以视图的内容或尺寸为基础的布局,比精确的指定视图的范围更加方便。 1、fill_parent 设置一个视图的布局为fill_parent将强制性的使视图扩展至它父元素的大小 2、match_parent 和fill_parent一样,从字面上的意思match_parent更贴切一些,于是从2.2开始,两个属性都可以使用,但2.3版本以后的建议使