模板&泛型编程

我们如果要写一个通用的加法函数,那么会有哪些方法实现呢?

1.函数重载

int Add(int left, int right)
{
	return left + right;
}

float Add(float left, float right)
{
	return left + right;
}

[缺点]

①要是有新的类型出现,就需要添加一个新的函数。函数重载的函数体相同,代码复用率不高,。要是一个函数体出错,其他的都得改;

②如果只是函数类型不同,参数列表相同,不能实现。

2.使用公共基类, 将通用的代码放在公共的基础类里面,让需要这部分功能的类去继承它。

[缺点]

①失去类型检查的优点;

②继承使代码更加难维护。

3.使用特殊的预处理

#define Add() ((x)+(y))

[缺点]

宏不是函数,不可以进行类型检测,安全性不高。


泛型编程:

编写与类型无关的逻辑代码,是代码复用的一种手段,模板是泛型编程的基础。

模板:

通俗来讲,就是依葫芦画瓢的代码生成器。(关键字:template)


函数模板

实际上是建立一个通用函数,这个函数与类型无关,用模糊类型来代表。


typename和class是可以定义模板的,但要注意struct是不可以定义的。


模板函数编译两次:

①实例化之前,进行简单的语法检测(一些可以检测出来,一些检测不出来);

②实例化期间,检查模板代码,查看是否所有的调用有效。

实例化:

实例化是指编译器用模板产生指定的类或者函数的特定类型版本,产生模板特定类型的过程。


隐式实例化:

Add(1,2)     Add(1.0f,2.0f)

显式实例化:

Add<>(1,2)     Add<int>(1,2)   Add<char>(1,'2')   Add<int>(1,'2')

:模板函数不是真正意义上的函数。


实参推演

从函数实参确定模板形参类型和值。

模板参数


注意:

1.模板形参名字只能在形参之后模板声明或定义的末尾之间使用,遵循名字屏蔽规则;

2.模板形参名字在同一模板形参中只能使用一次;

3.在函数模板的内部不能指定缺省的模板实参。

类型形参转换的两种情景(隐式实例化可转化的特例)

一般情况下,不会转换形参来匹配已有的实例化,会产生新的实例。

①接收const的引用或指针的函数用非const对象引用或指针调用。

②数组或函数类型转化为指针


非类型形参

模板内部定义常量的时候可以使用非类型形参

1.


2.

template <class T>
void FunTest(T arr,int size)
{
	for (int i = 0; i < size; ++i)
	{
		arr[i] = 0;
	}
}

模板函数重载

举个例子:


总结:

1.对于非模板函数和同名模板函数,要是其他条件相同,会优先调用非模板函数;

2.如果模板可以产生一个更好的匹配函数,则模板会产生一个实例;

3.若是显示给出一个空的模板函数列表,编译器会自动调用模板,所有的模板参数会根据实参演绎出来;

4.模板函数不能进行自动类型转化,而普通函数可以继续类型转化。

模板函数特化


看个例子:


这种情况就需要对模板进行特化

template<class T>
int mymax(T t1,T t2)
{
	return strcmp(t1, t2);
}

template<>
int mymax<const char*>(const char* const t1, const char* const t2)
{
	return strcmp(t1, t2);
}

int main()
{
	const char* p1 = "123";
	const char* p2 = "abc";
	cout<<mymax(p1, p2)<<endl;
	system("pause:");
	return 0;
}
模板类其实原理和模板函数类似,下节中我们会介绍到。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值