您好,欢迎访问三七文档
当前位置:首页 > 商业/管理/HR > 经营企划 > C++进阶课程讲义_v1.0.4
轻松入门实战应用传智播客C++课程传智播客C++进阶课程讲义传智扫地僧6、函数模板和类模板前言C++提供了函数模板(functiontemplate)。所谓函数模板,实际上是建立一个通用函数,其函数类型和形参类型不具体指定,用一个虚拟的类型来代表。这个通用函数就称为函数模板。凡是函数体相同的函数都可以用这个模板来代替,不必定义多个函数,只需在模板中定义一次即可。在调用函数时系统会根据实参的类型来取代模板中的虚拟类型,从而实现了不同函数的功能。1)C++提供两种模板机制:函数模板、类模板2)类属——类型参数化,又称参数模板使得程序(算法)可以从逻辑功能上抽象,把被处理的对象(数据)类型作为参数传递。总结:模板把函数或类要处理的数据类型参数化,表现为参数的多态性,称为类属。模板用于表达逻辑结构相同,但具体数据元素类型不同的数据对象的通用行为。轻松入门实战应用传智播客C++课程6.1函数模板6.1.1为什么要有函数模板需求:写n个函数,交换char类型、int类型、double类型变量的值。案例:#includeiostreamusingnamespacestd;/*voidmyswap(int&a,int&b){intt=a;a=b;b=t;}voidmyswap(char&a,char&b){chart=a;a=b;b=t;}*///template关键字告诉C++编译器我要开始泛型了.你不要随便报错//数据类型T参数化数据类型templatetypenameTvoidmyswap(T&a,T&b){Tt;t=a;a=b;b=t;}voidmain(){//chara='c';intx=1;inty=2;myswap(x,y);//自动数据类型推导的方式轻松入门实战应用传智播客C++课程floata=2.0;floatb=3.0;myswap(a,b);//自动数据类型推导的方式myswapfloat(a,b);//显示类型调用couthello...endl;system(pause);return;}6.1.2函数模板语法函数模板定义形式template类型形式参数表类型形式参数的形式为:typenameT1,typenameT2,……,typenameTn或classT1,classT2,……,classTn函数模板调用myswapfloat(a,b);//显示类型调用myswap(a,b);//自动数据类型推导轻松入门实战应用传智播客C++课程6.1.3函数模板和模板函数6.1.4函数模板做函数参数#includeiostreamusingnamespacestd;templatetypenameT,typenameT2voidsortArray(T*a,T2num){Ttmp;inti,j;for(i=0;inum;i++){for(j=i+1;jnum;j++){if(a[i]a[j]){tmp=a[i];a[i]=a[j];a[j]=tmp;}}}轻松入门实战应用传智播客C++课程}templateclassTvoidpirntArray(T*a,intnum){inti=0;for(i=0;inum;i++){couta[i];}}voidmain(){intnum=0;chara[]=ddadeeettttt;num=strlen(a);printf(排序之前\n);pirntArraychar(a,num);sortArraychar,int(a,num);//显示类型调用模板函数printf(排序之后\n);pirntArraychar(a,num);couthello...endl;system(pause);return;}6.1.5函数模板遇上函数重载函数模板和普通函数区别结论:/*函数模板不允许自动类型转化普通函数能够进行自动类型转换*/函数模板和普通函数在一起,调用规则:/*1函数模板可以像普通函数一样被重载2C++编译器优先考虑普通函数3如果函数模板可以产生一个更好的匹配,那么选择模板4可以通过空模板实参列表的语法限定编译器只通过模板匹配*/轻松入门实战应用传智播客C++课程案例1:#includeiostreamusingnamespacestd;templatetypenameTvoidmyswap(T&a,T&b){Tt;t=a;a=b;b=t;coutmyswap模板函数doendl;}voidmyswap(char&a,int&b){intt;t=a;a=b;b=t;coutmyswap普通函数doendl;}voidmain(){charcData='a';intiData=2;//myswapint(cData,iData);//结论函数模板不提供隐式的数据类型转换必须是严格的匹配myswap(cData,iData);//myswap(iData,cData);couthello...endl;system(pause);return;}案例2:#includeiostreamusingnamespacestd;轻松入门实战应用传智播客C++课程intMax(inta,intb){coutintMax(inta,intb)endl;returnab?a:b;}templatetypenameTTMax(Ta,Tb){coutTMax(Ta,Tb)endl;returnab?a:b;}templatetypenameTTMax(Ta,Tb,Tc){coutTMax(Ta,Tb,Tc)endl;returnMax(Max(a,b),c);}voidmain(){inta=1;intb=2;coutMax(a,b)endl;//当函数模板和普通函数都符合调用时,优先选择普通函数coutMax(a,b)endl;//若显示使用函数模板,则使用类型列表coutMax(3.0,4.0)endl;//如果函数模板产生更好的匹配使用函数模板coutMax(5.0,6.0,7.0)endl;//重载coutMax('a',100)endl;//调用普通函数可以隐式类型转换system(pause);return;}6.1.6C++编译器模板机制剖析思考:为什么函数模板可以和函数重载放在一块。C++编译器是如何提供函数模板机制的?轻松入门实战应用传智播客C++课程编译器编译原理什么是gccgcc(GNUCCompiler)编译器的作者是RichardStallman,也是GNU项目的奠基者。什么是gcc:gcc是GNUCompilerCollection的缩写。最初是作为C语言的编译器(GNUCCompiler),现在已经支持多种语言了,如C、C++、Java、Pascal、Ada、COBOL语言等。gcc支持多种硬件平台,甚至对DonKnuth设计的MMIX这类不常见的计算机都提供了完善的支持gcc主要特征1)gcc是一个可移植的编译器,支持多种硬件平台2)gcc不仅仅是个本地编译器,它还能跨平台交叉编译。3)gcc有多种语言前端,用于解析不同的语言。4)gcc是按模块化设计的,可以加入新语言和新CPU架构的支持5)gcc是自由软件gcc编译过程预处理(Pre-Processing)编译(Compiling)汇编(Assembling)链接(Linking)Gcc*.c–o1exe(总的编译步骤)Gcc–E1.c–o1.i//宏定义宏展开Gcc–S1.i–o1.sGcc–c1.s–o1.oGcc1.o–o1exe结论:gcc编译工具是一个工具链。。。。hello程序是一个高级C语言程序,这种形式容易被人读懂。为了在系统上运行hello.c程序,每条C语句都必须转化为低级机器指令。然后将这些指令打包成可执行目标文件格式,并以二进制形式存储器于磁盘中。gcc常用编译选项选项作用-o产生目标(.i、.s、.o、可执行文件等)-c通知gcc取消链接步骤,即编译源码并在最后生成目标文件-E只运行C预编译器-S告诉编译器产生汇编语言文件后停止编译,产生的汇编语言文件扩展名为.s轻松入门实战应用传智播客C++课程-Wall使gcc对源文件的代码有问题的地方发出警告-Idir将dir目录加入搜索头文件的目录路径-Ldir将dir目录加入搜索库的目录路径-llib链接lib库-g在目标文件中嵌入调试信息,以便gdb之类的调试程序调试练习gcc-Ehello.c-ohello.i(预处理)gcc-Shello.i-ohello.s(编译)gcc-chello.s-ohello.o(汇编)gcchello.o-ohello(链接)以上四个步骤,可合成一个步骤gcchello.c-ohello(直接编译链接成可执行目标文件)gcc-chello.c或gcc-chello.c-ohello.o(编译生成可重定位目标文件)建议初学都加这个选项。下面这个例子如果不加-Wall选项编译器不报任何错误,但是得到的结果却不是预期的。#includestdio.hintmain(void){printf(2+1is%f,3);return0;}Gcc编译多个.chello_1.hhello_1.cmain.c一次性编译gcchello_1.cmain.c–onewhello独立编译gcc-Wall-cmain.c-omain.ogcc-Wall-chello_1.c-ohello_fn.ogcc-Wallmain.ohello_1.o-onewhello模板函数反汇编观察命令:g++-S7.cpp-o7.s.file7.cpp.text.def__ZL6printfPKcz;.scl3;.type32;.endef__ZL6printfPKcz:LFB264:.cfi_startproc轻松入门实战应用传智播客C++课程pushl%ebp.cfi_def_cfa_offset8.cfi_offset5,-8movl%esp,%ebp.cfi_def_cfa_register5pushl%ebxsubl$36,%esp.cfi_offset3,-12leal12(%ebp),%eaxmovl%eax,-12(%ebp)movl-12(%ebp),%eaxmovl%eax,4(%esp)movl8(%ebp),%eaxmovl%eax,(%esp)call___mingw_vprintfmovl%eax,%ebxmovl%ebx,%eaxaddl$36,%esppopl%ebx.cfi_restore3popl%ebp.cfi_restore5.cfi_def_cfa4,4ret.cfi_endprocLFE264:.lcomm__ZStL8__ioinit,1,1.def___main;.scl2;.type32;.endef.section.rdata,drLC0:.asciia:%db:%d\12\0LC1:.asciic1:%cc2:%c\12\0LC2:.asciipause\0.text.globl_main.def_main;.scl2;.type32;.endef_main:LFB1023:.cfi_startproc.cfi_personality0,___gxx_personality_v0.cfi_lsda0,LLSDA1023pushl%ebp轻松入门实战应用传智播客C++课程.cfi_def_cfa_offset8.cfi_offset5,-8movl%esp,%ebp.cfi_def_cfa_register5andl$-16,%espsubl$32,%espcall___mainmovl$0,28(%esp)movl$10,24(%esp)movb$97,23(%esp)movb$98,
本文标题:C++进阶课程讲义_v1.0.4
链接地址:https://www.777doc.com/doc-4217053 .html