8.6 C++ 泛型化编程态
C/C++语言是一种通用的编程语言,具有高效、灵活和可移植等特点。C语言主要用于系统编程,如操作系统、编译器、数据库等;C语言是C语言的扩展,增加了面向对象编程的特性,适用于大型软件系统、图形用户界面、嵌入式系统等。C/C++语言具有很高的效率和控制能力,但也需要开发人员自行管理内存等底层资源,对于初学者来说可能会有一定的难度。
函数模板的基本使用: 函数模板就是要实现类型参数化,实现泛型编程,就是可以动态的调整数据类型.
#include <iostream>
#include <typeinfo>
using namespace std;
// template<> 告诉编译器,下面如果出现T不要报错,T是一个通用的类型
template<class T>
void MySwap(T &x, T &y)
{
T tmp = x;
x = y;
y = tmp;
}
template<class T>
T MyAdd(T &x, T &y)
{
return x + y;
}
// 此处的typename = class
template<typename T>
void MyPrint()
{
T number;
cout << "type = " << typeid(T).name() << endl;
}
int main(int argc, char *argv[])
{
// 自动类型推导: 必须要有参数才能推到(根据参数来确定类型)
int x = 10, y = 20;
MySwap(x, y);
cout << "x= " << x << endl;
int ret = MyAdd(x, y);
cout << "x+y = " << ret << endl;
// 手动类型指定: 如果参数不一致,可能会报错,此时我们需要告诉它类型
MySwap<int>(x, y);
cout << "x= " << x << endl;
// 针对无参数函数处理: 有些函数没有参数,我们需要指定模板默认类型
MyPrint<int>();
MyPrint<double>();
system("pause");
return 0;
}
我们在上面的案例基础上进行一定的加强,通过模板实现一个选择排序,我们可以传入任意的数据类型,都可被解析.
#include <iostream>
#include <typeinfo>
using namespace std;
template<class T>
void MySwap(T &x, T &y)
{
T tmp = x;
x = y;
y = tmp;
}
template<class T>
void SelectSort(T Array[], int len)
{
for (int x = 0; x < len; x++)
{
int max = x;
for (int y = x + 1; y < len; y++)
{
if (Array[max] > Array[y])
max = y;
}
if (max != x)
MySwap(Array[max], Array[x]);
}
}
template<class T>
void MyPrint(T Array[], int len)
{
for (int x = 0; x < len; x++)
cout << Array[x] << " ";
}
int main(int argc,char *argv[])
{
int Int_Array[10] = { 4, 7, 8, 2, 1, 8, 0, 3, 2, 7 };
SelectSort<int>(Int_Array, 10);
MyPrint<int>(Int_Array, 10);
char Char_Array[] = "hello lyshark";
int len = sizeof(Char_Array) / sizeof (char);
SelectSort<char>(Char_Array, len);
MyPrint<char>(Char_Array, len);
system("pause");
return 0;
}
实现模板具体化: 通过自定义模板函数,解决模板的局限性问题.
#include <iostream>
using namespace std;
class Student
{
public:
char *m_name;
int m_age;
public:
Student(char *name, int age)
{
this->m_name = name;
this->m_age = age;
}
};
template<class Student>
bool MyCompare(Student &x, Student &y)
{
if (x.m_age == y.m_age)
return true;
return false;
}
int main(int argc, char *argv[])
{
Student stu1("lyshark", 22);
Student stu2("admin", 33);
bool ret = MyCompare(stu1, stu1);
cout << ret << endl;
bool ret1 = MyCompare(stu1, stu2);
cout << ret1 << endl;
system("pause");
return 0;
}
定义并使用类模板: 类模板不支持类型的自动推导,所以必须在调用时Student<string, int>
显式指定好类型.
#include <iostream>
#include <string>
using namespace std;
template<class NameType = string,class AgeType = int> // 类模板可以指定默认参数
class Student
{
public:
string m_name;
int m_age;
public:
Student(NameType name,AgeType age)
{
this->m_name = name;
this->m_age = age;
}
void show() { cout << "name = " << m_name << endl; }
};
template<class Student>
bool MyCompare(Student &x, Student &y)
{
if (x.m_age == y.m_age)
return true;
return false;
}
int main(int argc, char *argv[])
{
// 调用类模板是要在类后面添加参数列表
Student<string, int> stu1("lyshark", 25);
stu1.show();
system("pause");
return 0;
}
类模板做函数参数传递: 此处我们将类模板Student<string, int>
当做函数参数传递给MyPrint
函数.
#include <iostream>
#include <string>
using namespace std;
template<class NameType,class AgeType>
class Student
{
public:
string m_name;
int m_age;
public:
Student(NameType name,AgeType age)
{
this->m_name = name;
this->m_age = age;
}
void show() { cout << "name = " << m_name << endl; }
};
void MyPrintA(Student<string, int> &ptr)
{ ptr.show(); }
template<class T1,class T2>
void MyPrintB(Student<T1,T2> &ptr)
{ ptr.show(); }
template<class T>
void MyPrintC(T &ptr)
{ ptr.show(); }
int main(int argc, char *argv[])
{
// 1. 指定传入的类型直接调用
Student<string, int> stu1("lyshark", 25);
MyPrintA(stu1);
// 2. 参数模板化调用
Student<string, int> stu2("admin", 10);
MyPrintB(stu2);
// 3.整体模板化调用
Student<string, int> stu3("root", 10);
MyPrintC(stu3);
system("pause");
return 0;
}
类模板类内定义类外实现: 类模板同样支持类内定义模板类型,在类外部对其进行具体的实现.
#include <iostream>
#include <string>
using namespace std;
template<class NameType,class AgeType>
class Student
{
public:
string m_name;
int m_age;
public:
Student(NameType name, AgeType age);
void show();
};
// 类外实现成员构造函数
template <class NameType,class AgeType>
Student<NameType, AgeType>::Student(NameType name, AgeType age)
{
this->m_name = name;
this->m_age = age;
}
// 类外实现打印函数
template <class NameType,class AgeType>
void Student<NameType, AgeType>::show()
{
cout << "Name = " << this->m_name << endl;
}
int main(int argc, char *argv[])
{
Student<string, int> stu("lyshark", 20);
stu.show();
system("pause");
return 0;
}
类模板友元函数类内实现: 友元函数就是可以让类外直接访问的函数,调用类内友元函数就像调用全局函数一样.
#include <iostream>
#include <string>
using namespace std;
template<class NameType,class AgeType>
class Student
{
// 友元函数的类内实现
friend void show(Student<NameType, AgeType> &ptr)
{
cout << "name = " << ptr.m_name << endl;
}
private:
string m_name;
int m_age;
public:
Student(NameType name, AgeType age)
{
this->m_name = name;
this->m_age = age;
}
};
int main(int argc, char *argv[])
{
Student<string, int> stu("lyshark", 20);
// 此处调用,类似于全局调用
show(stu);
system("pause");
return 0;
}
类模板友元函数类外实现: 类外实现同理,就是现在类内声明类型作为占位符,然后在类外进行实现.
#include <iostream>
#include <string>
using namespace std;
// 类外实现必须提前声明模板的存在
template<class T1, class T2> class Student;
template<class T1, class T2> void show(Student<T1, T2> & p);
template<class T1,class T2>
class Student
{
// 友元函数类内实现,利用空参数列表声明 (占位符)
friend void show<>(Student<T1, T2> &ptr);
private:
string m_name;
int m_age;
public:
Student(T1 name, T2 age)
{
this->m_name = name;
this->m_age = age;
}
};
// 对友元函数的类外实现
template<class T1,class T2>
void show(Student<T1,T2> &ptr)
{
cout << "name = " << ptr.m_name << endl;
}
int main(int argc, char *argv[])
{
Student<string, int> stu("lyshark", 20);
// 此处调用,类似于全局调用
show(stu);
system("pause");
return 0;
}
8.6 C++ 泛型化编程态的更多相关文章
- Java中的泛型 --- Java 编程思想
前言 我一直都认为泛型是程序语言设计中一个非常基础,重要的概念,Java 中的泛型到底是怎么样的,为什么会有泛型,泛型怎么发展出来的.通透理解泛型是学好基础里面中非常重要的.于是,我对<Ja ...
- 从xfire谈WebService接口化编程
前段时间有博友在看我的博文<WebService入门案例>后,发邮件问我关于WebService 接口在java中的开发,以及在实际生产环境中的应用.想想自己入职也有一段时间了,似乎也该总 ...
- Deep Learning 2_深度学习UFLDL教程:矢量化编程(斯坦福大学深度学习教程)
1前言 本节主要是让人用矢量化编程代替效率比较低的for循环. 在前一节的Sparse Autoencoder练习中已经实现了矢量化编程,所以与前一节的区别只在于本节训练集是用MINIST数据集,而上 ...
- 6.6.2 自己主动泛型化(automatic generalization)
6.6.2 自己主动泛型化(automatic generalization) 在这一章,我们已经实现了几个 F# 的高阶函数.也看到了在 F# 和 C# 中并排的实现.F# 实现的非常重要方面,是我 ...
- React 面向组件化编程 - 封装了webpack - npm run build 产生的包的 /static 引用路径问题
React 面向组件化编程 面向对象 ----> 面向模块 ----> 面向组件 套路: 注意: 组件名必须大写开头: 只能有一个根标签: <input />虚拟DOM 元素必 ...
- c++以代理的方式来实现接口化编程
假如你项目代码本身已经实现了很多的实体类,但并未采用接口,可以考虑以这种方式来实现接口化编程 struct ITest { virtual void Test()=0; }; class CTes ...
- linux无锁化编程--__sync_fetch_and_add系列原子操作函数
linux支持的哪些操作是具有原子特性的?知道这些东西是理解和设计无锁化编程算法的基础. 下面的东西整理自网络.先感谢大家的分享! __sync_fetch_and_add系列的命令,发现这个系列命令 ...
- 初探CORBA组件化编程
1.掌握组件化开发的概念,了解CORBA模型及ORB机制:2.掌握CORBA组件编程方法.二.实验内容(一).步骤1.配制环境JDK环境.2.编写编译IDL接口.3.编写编译服务端程序.4.编写编译客 ...
- vue组件化编程应用2
写几个小案例来理解vue的组件化编程思想,下面是一个demo. 效果图示: 需求: header部输入任务,进行添加,在list中显示; list中每个item项,鼠标移入时,背景变灰并显示delet ...
- vue组件化编程应用
写几个小案例来理解vue的组件化编程思想,下面是一个demo. 效果图示: 功能: Add组件用于添加用户评论,提交后右边评论回复会立马显示数据.Item组件点击删除可以删除当前用户评论.当List组 ...
随机推荐
- 【python爬虫】requests高级用法 代理池搭建 爬虫实战
目录 昨日回顾 面试题 爬虫总结 今日内容 1 requests高级用法 1.0 解析json 1.1 ssl认证(了解) 1.2 使用代理(重要) 1.3 超时设置 1.4 异常处理 1.5 上传文 ...
- wscat 命令报错
使用wscat测试连接时报错: [root@kafka kafka-logs]# wscat ws://xxx.xxx.com/bs /usr/lib/node_modules/wscat/node_ ...
- C# 内存缓存工具类 MemoryCacheUtil
C# 内存缓存工具类 MemoryCacheUtil using System; using System.Collections.Concurrent; using System.Collectio ...
- vivo 商城前端架构升级-总览篇
本文首发于 vivo互联网技术 微信公众号链接: https://mp.weixin.qq.com/s/vD9yvYNaxTQBLABik6aqNg作者:官网商城前端团队 [背景] 一年前 vivo ...
- mysql备份恢复总结
mysqldump备份注:例子中的语句都是在mysql5.6下执行------------------基础------------------------一.修改my.cnf文件 vi /etc/my ...
- springboot2.0+dubbo-spring-boot-starter聚合项目打可执行的jar包
springboot2.0+dubbo聚合项目打可执行的jar包 springboot2.0+dubbo-spring-boot-starter项目服务方打包和以前老版本的dubbo打包方式不一样,不 ...
- Java21 + SpringBoot3集成Spring Data JPA
.markdown-body { line-height: 1.75; font-weight: 400; font-size: 16px; overflow-x: hidden; color: rg ...
- 使用Amber计算单点能三步走
技术背景 Amber是一个在分子动力学中非常常用的一个软件,可以用于进行分子动力学模拟计算,可以与一些软件配合进行增强采样.这里我们简单介绍一下如何使用Amber去计算一个分子构象的单点势能值,及其对 ...
- 浏览器兼容 : IE 5 到 IE 9
<!--[if IE]> <link href="ie.css" rel="stylesheet"> <![endif]--> ...
- 类外static函数定义要不要加static关键字?
类外static函数定义要不要加static关键字? 先说答案:不需要. 错误代码: #include<iostream> #include<memory> using nam ...