为什么要引入模板:为了避免代码重复,程序员可以编写脱离数据类型通用模板。

模板的分类:函数模板 + 类模板

注意:模板的声明或定义只能在全局,命名空间或类范围内进行。不能在函数内进行,比如不能在main函数中声明或定义一个模板。

函数模板:

定义:

函数模板:关键词在后两个字,模板:提供一类函数的抽象,以任意类型T为参数把具有相同程序正文的一类函数抽象出来,可以适合任意类型T的参数。

模板函数:重点在函数,是对函数模板进行参数实例化后的结果,是一个具体的函数。

什么时候使用函数模板:会有一类函数,它们几乎相同,唯一的区别就是形参类型不同。这时我们可以撇开不同的数据类型,创建一个模板,并把数据类型也当作一个参数而设计一个模板

举例说明:编写比较两个整型数据大小的函数,它只适合于整型数据。如果是比较两个浮点型数据,就需要重新编写另外一个函数。如果我们使用函数模板的话,可以把数据类型忽略,编写一个max函数,既可以实现int,也可以实现浮点型。

语法:

template <class T>   //模板声明格式
返回值类型 函数名(模板形参表) //模板函数形参表
{
//函数定义体
}
函数调用:函数名(模板实参表) //和普通的函数调用没有区别,只不过运行时,系统会首先根据参数类型确定数据类型,生成一个模板函数。

说明:

1、这里的class指一类的意思

2、参数有两种:类型参数 + 函数参数

3、T 为类型参数,可以是预定义的数据类型,可以是用户自定义的类型(类,结构体等)。在运行中必须用实际的数据类型替代它

4、template 语句 和 函数模板定义语句不允许有别的语句

如:

    template <class T>
int i; //这是不允许的.
T max(T a , T b)
{
return (a>b)?a:b;
}

举例:求两个数最大值,使用模板

    template <class T>
T max(T a , T b)
{
return (a>b)?a:b;
}
调用:
int i1,i2;
flaot f1,f2;
max(i1,i2);
max(f1,f2);

运行过程可分两部分:

第一、传递参数类型:用模板实参int将 类型参数T进行实例化。即用 int  代替T

第二、传递参数:把参数传递给函数

函数模板的重载:

引入函数模板重载的原因:函数模板要求要传入参数类型必须全都相同,不同则报错。使用函数模板重载就是要解决这个问题

引入两种方法解决这个问题:

1、函数模板可以使用多个模板参数:有几个不同的类型,就是用不同的模板参数来代表它。

2、超载一个函数模板:定义一个模板后,在定义一个超载函数

具体来说:

1、定义一个多参的函数模板:

    template <class T,class D>
T max(T a,D b)
{
return (a>b)?a:b;
}

调用:

int a;float b;
max(a,b)

2、超载一个函数模板

    template <class T>
T max(T a,T b)
{
return (a>b)?a:b;
}
int max(int,int);//用户自己定义一个同名函数
    参数调用:int m,n;
char a,b;
char s[10];
max(m,n);//调用函数 实参和函数的参数类型完全一致,直接调用函数
max(a,b);//调用模板 实参和函数参数类型不同,直接掉模板
max(m,a);//调用函数 实参的类型不同,模板不适合,则再次调用函数
max(m,s);//报错-函数也不适合,直接报错

分析:调用函数时的顺序:先调用函数 ---  其次套用模板  --- 再调用函数 --- 报错

运行步骤:

如果调用语句的实参类型和函数类型完全一致,这时不找模板,而优先使用函数。

如果调用语句的实参类型和函数类型不一致,应该找模板

如果调用语句的实参各自类型不同,应重新调用函数,并试着把实参类型转换为形参类型,成功则调用,失败,则报错

函数模板和类结合

举例:

    #include <iostream>
using namespace std;
class Point
{
private:
int x;
public:
Point(int x1);
bool operator>(const Point& p);
friend ostream& operator<<(ostream& cout,const Point& p);
};
Point::Point(int x1)
{
x=x1;
}
bool Point::operator>(const Point& p)
{
return (x>p.x)?true:false;
}
ostream& operator<<(ostream& cout,const Point& p)
{
cout<<p.x;
return cout;
}
template <class T>
T& max(T& a,T& b)
{
cout<<"调用函数模板"<<endl;
return (a>b)?a:b;
}
void main()
{
Point a(1);
Point b(2);
cout<<max(a,b);
system("pause");
}

什么时候使用模板:

1、创建一个类型安全的集合类(如,堆栈)用来处理各种类型的数据

2、为函数添加额外的类型检查以避免获得空指针

模板的优势:为函数大多数以上应用可以不用模板实现

模板具有以下几个优势:

1、开发容易。你可以只为你的类或函数创建一个普通的版本代替手工创建特殊情况处理。

2、理解容易。模板为抽象类型信息提供了一个直截了当的方法。

3、类型安全。模板使用的类型在编译时是明确的,编译器可以在发生错误之前进行类型检查。

C++ 函数模板基础知识的更多相关文章

  1. C++ 类模板基础知识

    类模板与模板类 为什么要引入类模板:类模板是对一批仅仅成员数据类型不同的类的抽象,程序员只要为这一批类所组成的整个类家族创建一个类模板,给出一套程序代码,就可以用来生成多种具体的类,(这类可以看作是类 ...

  2. Django模板-基础知识

    上一篇中带参数的URLconf虽然可以做到传参动态显示内容,但是最终现实的内容还是硬编码到Python代码中的 def hours_ahead(request,phours): try: phours ...

  3. JS中函数的基础知识

    函数 一.  函数定义 函数又叫方法,在程序里面函数是用来执行某些特定功能的代码.为了减少重复使用代码,可以把特定功能的代码做成函数,需要使用时拿出来调用.alert();就是一个很常见的.简单的函数 ...

  4. smarty模板基础知识

    1.定义 Smarty是一个使用php写出来的模板引擎,它分离了逻辑代码和外在的内容,提供了一种易于管理和使用的方法,用来将原本与html代码混杂在一起PHP代码逻辑分离. 简单的讲,目的就是要使PH ...

  5. python学习9 函数的基础知识

    1.函数的定义 def  func(): 2.函数的调用 func() 3.函数的返回值 #1.没有返回值 # (1)不写return # (2)只写return后面的代码不在继续执行,返回空,代表结 ...

  6. javascript 函数的基础知识

    1. Why JavaScript functions always return a value? I'm taking a course in JavaScript programming, an ...

  7. [转]C++函数模板与模板函数

      1.函数模板的声明和模板函数的生成   1.1函数模板的声明 函数模板可以用来创建一个通用的函数,以支持多种不同的形参,避免重载函数的函数体重复设计.它的最大特点是把函数使用的数据类型作为参数. ...

  8. Python基础知识详解 从入门到精通(七)类与对象

    本篇主要是介绍python,内容可先看目录其他基础知识详解,欢迎查看本人的其他文章Python基础知识详解 从入门到精通(一)介绍Python基础知识详解 从入门到精通(二)基础Python基础知识详 ...

  9. Greenplum入门——基础知识、安装、常用函数

    Greenplum入门——基础知识.安装.常用函数 2017年10月08日 22:03:09 在咖啡里溺水的鱼 阅读数:8709    版权声明:本文为博主原创,允许非商业性质转载但请注明原作者和出处 ...

随机推荐

  1. V4L2应用程序框架【转】

    转自:https://www.cnblogs.com/hzhida/archive/2012/05/29/2524397.html V4L2是V4L的升级版本,linux下视频设备程序提供了一套接口规 ...

  2. MySQL 误操作后数据恢复(update,delete忘加where条件)【转】

    在数据库日常维护中,开发人员是最让人头痛的,很多时候都会由于SQL语句 写的有问题导致服务器出问题,导致资源耗尽.最危险的操作就是在做DML操作的时候忘加where条件,导致全表更新,这是作为运维或者 ...

  3. dynamic web module和对应的TOMCAT 版本

    大致因为java的web系统有多种类型,比如静态的和动态的,然后动态的java web project要设置dynamic web module,也就是动态网页模型,他必须要和对应的服务器搭配好了才能 ...

  4. 前端工程化之webpack中配置babel-loader(四)

    安装 安装:npm i -D babel-core babel-loader babel-plugin-transform-runtime 安装:npm i -D babel-preset-es201 ...

  5. 判断iframe加载完成、用于当ifame加载完成时执行一些操作

    window.frames["iframec"].addEventListener( "load", function(){ window.frames[&qu ...

  6. ERP合同管理二(三十)

    未审核表单列表显示: 1.用户登录后,根据登录用户加载审核流程表中属于当前登录用户的未审核表单.2.点击选中未审核表单跳转到指定审核流程页面 if (Request.QueryString[" ...

  7. ERP完善合同起草(二十八)

    前端的代码: <%@ Page Language="C#" AutoEventWireup="true" CodeBehind="CRMCont ...

  8. Javascript面向对象基础(二)

    一: 用定义函数的方式定义类在面向对象的思想中,最核心的概念之一就是类.一个类表示了具有相似性质的一类事物的抽象,通过实例化一个类,可以获得属于该类的一个实例,即对象.在JavaScript中定义一个 ...

  9. mongosync同步1,oplog同步会读取其他集合同步

    使用mongosync同步数据     注意: 我下面的这个mongodb版本较低(3.2.16), 还可以用这个工具来同步数据.工具不支持更高版本的mongodb了. 使用方法: https://g ...

  10. BZOJ4972 八月月赛 Problem B 小Q的方格纸 二维前缀和

    欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - BZOJ4972 八月月赛Problem B 题目概括 一个矩阵,一坨询问,问矩阵中一个特定方向的等腰直角三角 ...