C++模板类与继承

news2024/11/20 18:40:11

目录

分类

一、模板类不继承

(1)代码

(2)分析

(3)运行结果

二、模板类继承普通类

(1)代码

(2)分析

(3)运行结果

三、普通类继承模板类的实例版本

(1)代码

(2)分析

3)运行结果

四、普通类继承模板类(常见)(模板类含通用类型参数)

(1)代码

(2)分析

(3)运行结果

五、模板类继承模板类

(1)代码

(2)分析

(3)运行结果

 六、模板类继承模板参数给出的基类(不能是模板类)

(1)代码

(2)分析

(3)运行结果


分类

1)模板类继承普通类(常见)

2)普通类继承模板类的实例版本

3)普通类继承模板类(常见)

4)模板类继承模板类

5)模板类继承模板参数给出的基类(不能是模板类)

一、模板类不继承

(1)代码

#include<iostream>
using namespace std;

//模板类BB
template<class T1,class T2>
class BB
{
	public:
		T1 m_x;
		T2 m_y;
		BB(const T1 x,const T2 y):m_x(x),m_y(y){cout<<"调用了BB的构造函数。"<<endl;}
		void fun2()const{cout<<"调用了func2()函数:x="<<m_x<<",y="<<m_y<<endl;}
};

int main()
{
	BB<int,string>bb(8,"我是一只小猫咪。");
	bb.fun2();
	return 0;
}

(2)分析

①模板类BB直接实例化,不继承其他类。

(3)运行结果

二、模板类继承普通类

(1)代码

//普通类AA作为基类,BB类作为派生类
#include<iostream>
using namespace std;

//AABB都没有默认的构造函数
//普通类AA
class AA
{
	public:
		int m_a;
		AA(int a):m_a(a){cout<<"调用了AA的构造函数。"<<endl;}
		void fun1(){cout<<"调用了func1()函数:m_a="<<m_a<<endl;}	
};

//模板类BB
template<class T1,class T2>
class BB:public AA    //111111继承普通类
{
	public:
		T1 m_x;
		T2 m_y;
		BB(const T1 x,const T2 y,int a):AA(a),m_x(x),m_y(y){cout<<"调用了BB的构造函数。"<<endl;}    //222222派生类的构造函数要调用基类的构造函数
		void fun2()const{cout<<"调用了func2()函数:x="<<m_x<<",y="<<m_y<<endl;}
};

int main()
{
	BB<int,string>bb(8,"我是一只小猫咪。",3);
	bb.fun2();
	bb.fun1();        //调用基类的func1()函数
	return 0;
}

(2)分析

①程序定义了一个普通类AA,模板类BB作为基类继承普通类AA

template<class T1,class T2>                 //加模板标签

class BB:public AA  

②只需要修改派生类BB的构造函数,调用基类AA的构造函数即可;

BB(const T1 x,const T2 y,int a):AA(a),m_x(x),m_y(y)

(3)运行结果

三、普通类继承模板类的实例版本

(1)代码

#include<iostream>
using namespace std;
//AABB都没有默认的构造函数
//模板类BB
template<class T1,class T2>
class BB
{
	public:
		T1 m_x;
		T2 m_y;
		BB(const T1 x,const T2 y):m_x(x),m_y(y){cout<<"调用了BB的构造函数。"<<endl;}
		void fun2()const{cout<<"调用了func2()函数:x="<<m_x<<",y="<<m_y<<endl;}
};

//普通类AA
class AA:public BB<int,string>    //普通类AA继承模板类BB
{
	public:
		int m_a;
		AA(int a,int x,string y):BB(x,y),m_a(a){cout<<"调用了AA的构造函数。"<<endl;}                            //派生类构造函数调用基类构造函数(初始化列表)
		void fun1(){cout<<"调用了func1()函数:m_a="<<m_a<<endl;}	
};

int main()
{
	AA aa(3,8,"我是一只小猫咪。");
	aa.fun1();        //调用派生类函数
	aa.fun2();        //调用基类函数
	return 0;
}

(2)分析

①普通类AA作为派生类继承模板类BB

AA只是继承BB的某一个实例化版本,普通类继承,没有特殊之处

class AA:public BB<int,string>                 //不需要加模板标签

②修改派生类AA的构造函数调用基类BB的构造函数即可

AA(int a,int x,string y):BB(x,y),m_a(a)

3)运行结果

四、普通类继承模板类(常见)(模板类含通用类型参数)

(1)代码

#include<iostream>
using namespace std;

//AABB都没有默认的构造函数
//模板类BB
template<class T1,class T2>
class BB
{
	public:
		T1 m_x;
		T2 m_y;
		BB(const T1 x,const T2 y):m_x(x),m_y(y){cout<<"调用了BB的构造函数。"<<endl;}
		void fun2()const{cout<<"调用了func2()函数:x="<<m_x<<",y="<<m_y<<endl;}
};

//模板类AA
template<class T1,class T2>    //11111BB的模板类标签复制下来
class AA:public BB<T1,T2>        //22222普通类继承通用模板类
{
	public:
		int m_a;            
		AA(int a,T1 x,T2 y):BB<T1,T2>(x,y),m_a(a){cout<<"调用了AA的构造函数。"<<endl;}                        //333333修改构造函数
		void fun1(){cout<<"调用了func1()函数:m_a="<<m_a<<endl;}	
};

int main()
{
	AA <int,string>aa(3,8,"我是一只小猫咪。");   //4444AA是一个模板类,需要模板标签
	aa.fun1();
	aa.fun2();
	return 0;
}

(2)分析

①普通类AA作为派生类继承模板类BB(非实例化)

要保留BB的通用类型,就需要把AA变成模板类

template<class T1,class T2>    //BB的模板类标签复制下来
class AA:public BB<T1,T2>        //普通类继承通用模板类

②修改派生类AA的构造函数调用基类BB的构造函数即可

AA(int a,T1 x,T2 y):BB<T1,T2>(x,y),m_a(a)

(3)运行结果

 

五、模板类继承模板类

(1)代码

#include<iostream>
using namespace std;
//AABB都没有默认的构造函数
//模板类BB
template<class T1,class T2>
class BB
{
	public:
		T1 m_x;
		T2 m_y;
		BB(const T1 x,const T2 y):m_x(x),m_y(y){cout<<"调用了BB的构造函数。"<<endl;}
		void fun2()const{cout<<"调用了func2()函数:x="<<m_x<<",y="<<m_y<<endl;}
};

//普通类AA
template<class T1,class T2>
class AA:public BB<T1,T2>
{
	public:
		int m_a;
		AA(int a,T1 x,T2 y):BB<T1,T2>(x,y),m_a(a){cout<<"调用了AA的构造函数。"<<endl;}
		void fun1(){cout<<"调用了func1()函数:m_a="<<m_a<<endl;}	
};

//模板类CC
template<class T,class T1,class T2>    //11111111CC类模板标签增加两个通用类型参数
class CC:public BB<T1,T2>              //22222222CC类继承BB类
{
	public:
		T m_a;
		CC(const T a,const T1 x,const T2 y):BB<T1,T2>(x,y),m_a(a){cout<<"调用了CC的构造函数。\n"<<endl;}              //CC类构造函数调用基类BB构造函数
		void fun3(){cout<<"调用了fun3()函数:m_a="<<m_a<<endl;}
};
int main()
{
	CC <int,int,string>cc(3,8,"我是一只小猫咪。");
	cc.fun3();
	cc.fun2();
	return 0;
}

(2)分析

①增加一个模板类CC

template<class T>
class CC
{
    public:
        T m_a;
        CC(const T a):m_a(a){cout<<"调用了CC的构造函数。\n"<<endl;}
        void fun3(){cout<<"调用了fun3()函数:m_a="<<m_a<<endl;}
};

②模板类CC继承BB

template<class T,class T1,class T2>    //CC类模板标签增加两个通用类型参数
class CC:public BB<T1,T2>              //CC类继承BB类

 ②修改派生类CC的构造函数调用基类BB的构造函数即可;

CC(const T a,const T1 x,const T2 y):BB<T1,T2>(x,y),m_a(a)

(3)运行结果

 

 

 六、模板类继承模板参数给出的基类(不能是模板类)

(1)代码

#include<iostream>
using namespace std;

//普通类AA
class AA
{
	public:
		AA(){cout<<"调用了AA的构造函数AA()。"<<endl;}
		AA(int a){cout<<"调用了AA的构造函数AA(int a)。"<<endl;}
};

//普通类BB
class BB
{
	public:
		BB(){cout<<"调用了BB的构造函数BB()。"<<endl;}
		BB(int a){cout<<"调用了BB的构造函数BB(int a)。"<<endl;}
};

//普通类CC
class CC
{
	public:
		CC(){cout<<"调用了CC的构造函数CC()。"<<endl;}
		CC(int a){cout<<"调用了CC的构造函数CC(int a)。"<<endl;}
};

//模板类DD
template<class T>
class DD
{
	public:
		DD(){cout<<"调用了DD的构造函数DD()。"<<endl;}
		DD(int a){cout<<"调用了DD的构造函数DD(int a)。"<<endl;}
};

//模板类EE
template<class T>
class EE:public T
{
	public:
		EE():T(){cout<<"调用了EE的构造函数EE()。"<<endl;}
		EE(int a):T(a){cout<<"调用了EE的构造函数EE(int a)。"<<endl;}
};

int main()
{
	EE<AA>ea1;//AA作为基类
	EE<BB>eb1;//BB作为基类
	EE<CC>ec1;//CC作为基类
	EE<DD<int>  >ed1; //DD<int>作为基类,模板类作为基类时,必须明确指出模板类型参数
	//EE<DD>ed1;  		 //DD作为基类,错误
	return 0;
}

 (2)分析

①EE是模板类,有一个通用模板类型参数,在继承时T可以是普通类,也可以是模板类;

②但是在继承模板类的时候需要指明基类的通用类型参数。

    EE<DD<int>  >ed1; //DD<int>(类名)作为基类,模板类作为基类时,必须明确指出模板类型参数
    //EE<DD>ed1;           //DD作为基类,错误

(3)运行结果

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/542526.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【TCP协议】TCP的运输连接管理-三次握手四次挥手

TCP 的运输连接管理 TCP 是面向连接的协议&#xff0c;运输连接是用来传送 TCP 报文的&#xff0c;TCP 的运输连接的建立和释放是每一次面向连接的通信中必不可少的过程。因此&#xff0c;运输连接就有三个阶段&#xff0c;即&#xff1a;连接建立、数据传输、连接释放。 TCP…

chatgpt赋能Python-python3_6_6怎么用

Python3.6.6的基本介绍 1. Python3的发展历程 自1991年Guido van Rossum创造了Python language以来&#xff0c;Python一直在不断发展和改进。Python3是Python中的最新版本&#xff0c;它对Python2进行了重大升级。Python3.6.6是Python3的一个稳定版本&#xff0c;其中包含了…

chatgpt赋能Python-python3_4安装numpy

Python3.4安装Numpy的SEO指南 Numpy是Python科学计算库之一&#xff0c;它提供了强大的支持&#xff0c;使您可以使用Python进行数学和科学计算。Numpy的安装是许多Python开发者必须掌握的技能&#xff0c;因为它是许多其他库的先决条件。在本SEO指南中&#xff0c;我们将介绍…

MATLAB信号处理:滤波器设计、频域分析和数字信号处理的应用和优化

章节一&#xff1a;引言 在现代科技领域中&#xff0c;信号处理起着至关重要的作用。它涵盖了从音频和图像处理到通信和生物医学工程等众多领域。MATLAB作为一种强大的数值计算软件&#xff0c;为信号处理提供了丰富的工具和函数&#xff0c;使得信号处理任务更加高效和可靠。…

chatgpt赋能Python-python3_6怎么下载

Python3.6如何下载&#xff1a;完全指南 Python 3.6是一种非常强大的编程语言&#xff0c;被广泛应用于各种应用程序和领域。如果你还没有安装Python 3.6&#xff0c;那么你已经错过了很多有趣的功能和工具。本文将向你介绍如何在各种操作系统上下载Python 3.6&#xff0c;无论…

在Vue项目中vue-quill-editor的安装与使用【详细图解+过程+包含图片的缩放拖拽】

Quill 官网&#xff1a;https://quilljs.com// 一、Quill的安装与使用&#xff08;初级&#xff09; 1、下载安装 npm install vue-quill-editor --save这里建议使用管理员命令窗口的形式&#xff0c;找到自己的项目&#xff0c;如下图所示。然后进行安装&#xff08;目的&a…

RBTree改造,并模拟实现setmap

目录 RBTree改造 给红黑树增加迭代器 前置 前置-- RBT细节改造 模拟set 模拟map RBTree改造 给红黑树增加迭代器 前置 前置的作用是找下一个较大的节点。 假如我们it指向的是5&#xff0c;it则是将it指向6。加入it指向的是7&#xff0c;则it则是将it指向8。 也就是说…

三十八、流控效果、

1、流控效果 流控效果是指请求达到流控阈值时应该采取的措施&#xff0c;包括三种&#xff1a; 快速失败&#xff1a;达到阈值后&#xff0c;新的请求会被立即拒绝并抛出FlowException异常。是默认的处理方式。 warm up&#xff1a;预热模式&#xff0c;对超出阈值的请求同样是…

chatgpt赋能Python-python3m

Python 3: 一个新时代的编程语言 在编程的世界里&#xff0c;Python 3可能是当前最为热门的编程语言。Python 3是Python语言的最新版本&#xff0c;代码更加现代化&#xff0c;更加简洁易懂&#xff0c;比Python 2更加易于使用。这篇文章将介绍Python 3的各种特性&#xff0c;…

Git回滚详解

文章目录 git restore撤销工作区文件更改撤销暂存区文件更改 git checkoutgit revert冲突解决具体操作 git resetreset 的作用第 1 步&#xff1a;移动 HEAD&#xff08;--soft&#xff09;第 2 步&#xff1a;更新暂存区&#xff08;--mixed&#xff09;第 3 步&#xff1a;更…

如何写好英文论文中的句子?(下)

1 前情提要 大家先看完上一篇文章如何写好英文论文中的句子&#xff1f;&#xff08;上&#xff09;&#xff0c;再接着往下翻。 10 先说名词&#xff0c;再用代词&#xff08;it、they&#xff09;指代该名词 11 否定词放在句子开头附近 12 否定词的正确位置&#xff1a;助动…

消息通知之系统层事件发布相关流程

前言 Openharmony 3.1Release中存在消息通知的处理&#xff0c;消息通知包括系统层事件发布、消息订阅、消息投递与处理&#xff0c;为了开发者能够熟悉消息的处理流程&#xff0c;本篇文章主要介绍系统层事件发布的相关流程。 整体流程 代码流程 发布消息 { eventAction)w…

自定义颜色编辑选取对话框

一、简介 Qt中已经有一些封装好的对话框&#xff0c;比如QMessageBox、QColorDialog等&#xff0c;使用起来快捷方便&#xff0c;但缺点是我们无法为它们自定义样式&#xff0c;所以可能难以“融入”我们的项目。既然如此&#xff0c;那就自己做一个把。抱着这样的想法&#x…

Android SELinux安全机制与权限管理那些事

文章目录 前言权限管理系统应用特权应用历史漏洞广播的保护机制CVE-2020-0391 SELinux 前言 在 Android 漏洞挖掘和安全研究过程中&#xff0c;不可避免地会涉及到跟 Android SELinux 安全机制打交道&#xff0c;比如当你手握一个 System 应用的路径穿越的漏洞的时候想去覆写其…

DS:基于鸢尾花数据集利用多种数据降维技术(PCA、SVD、MDS、LDA、T-SNE)实现三维可视化

DS&#xff1a;基于鸢尾花数据集利用多种数据降维技术(PCA、SVD、MDS、LDA、T-SNE)实现三维可视化 目录 基于鸢尾花数据集利用多种数据降维技术(PCA、SVD、MDS、LDA、T-SNE)实现三维可视化 # 1、加载示例数据集&#xff08;鸢尾花数据集&#xff09; # 2、数据预处理 # T1、…

媒体专访是品牌初创阶段宣传的重要手段

传媒如春雨&#xff0c;润物细无声&#xff0c;大家好&#xff0c;我是51媒体网胡老师。 很早以前&#xff0c;有位前辈跟我讲&#xff0c;人的成功分两种&#xff0c;一种是借助平台成功&#xff0c;一种是自己创业成功&#xff0c; 前者成功的概率很大&#xff0c;只需要选好…

【5.18】二、黑盒测试方法—因果图与决策表法

目录 2.3 因果图与决策表法 2.3.1 因果图设计法 2.3.2 决策表 2.3.3 实例&#xff1a;三角形决策表 2.3.4 实例&#xff1a;工资发放决策表 2.3 因果图与决策表法 等价类划分法与边界值分析法主要侧重于输入条件&#xff0c;却没有考虑这些输入之间的关系&#xff0c;如…

单链表和双向链表如何执行删除操作

在实际的软件开发中&#xff0c;从链表中删除一个数据无外乎这两种情况&#xff1a; 删除结点中“值等于某个给定值”的结点&#xff1b;删除给定指针指向的结点。 1.从头结点开始一个一个依次遍历对比&#xff0c;直到找到值等于给定值的结点&#xff0c;然后再通过我前面讲…

LeetCode高频算法刷题记录4

文章目录 1. 二叉树的最近公共祖先【中等】1.1 题目描述1.2 解题思路1.3 代码实现 2. 全排列【中等】2.1 题目描述2.2 解题思路2.3 代码实现 3. 相交链表【简单】3.1 题目描述3.2 解题思路3.3 代码实现 4. 合并 K 个升序链表【困难】4.1 题目描述4.2 解题思路4.3 代码实现 5. 环…

chatgpt赋能Python-python3_4怎么下载

Python3.4的下载和安装 Python是一种流行的编程语言&#xff0c;它被广泛用于算法学习、数据分析和网站开发等领域。Python3.4是Python编程语言的一个版本&#xff0c;它在性能和功能方面都得到了改进。如果你希望学习Python3.4或者使用它开发项目&#xff0c;那么你需要下载并…