搜索
首页后端开发C#.Net教程深度解析C++的函数模板与类模板

一、函数模板

1、定义

   template 2894498a3f911d23cd16997faa3262b8
   返回值类型 模板名 (形参表){
          函数体
   };

template <class T1, class T2>
T2 print(T1 arg1, T2 arg2)
{
    cout<< arg1 << " "<< arg2<<endl;
    return arg2;
}

2、不通过参数实例化函数模板

#include <iostream>
using namespace std;
template <class T>
T Inc(T n){
    return 1 + n;
}
int main(){
    cout << Inc<double>(4)/2; //输出 2.5
    return 0;
}

3、函数模板可以重载,只要它们的形参表或类型参数表不同即可

template<class T1, class T2>
void print(T1 arg1, T2 arg2) {
    cout<< arg1 << " "<< arg2<<endl;
}
template<class T>
void print(T arg1, T arg2) {
    cout<< arg1 << " "<< arg2<<endl;
}
template<class T,class T2>
void print(T arg1, T arg2) {
    cout<< arg1 << " "<< arg2<<endl;
}

4、函数模板和函数的次序

    在有多个函数和函数模板名字相同的情况下,编译器如下处理一条函数调用语句

  • 先找参数完全匹配的普通函数(非由模板实例化而得的函数)。

  • 再找参数完全匹配的模板函数。

  • 再找实参数经过自动类型转换后能够匹配的普通函数。

  • 上面的都找不到,则报错。

template <class T>
T Max( T a, T b) {
    cout << "TemplateMax" <<endl; return 0;
}
template <class T,class T2>
T Max( T a, T2 b) {
    cout << "TemplateMax2" <<endl; return 0;
}
double Max(double a, double b){
    cout << "MyMax" << endl; return 0;
}
int main() {
    Max( 1.2,3.4);     // 输出MyMax
    Max(4, 5);         //输出TemplateMax
    Max( 1.2, 3);      //输出TemplateMax2
    return 0;
}

5、匹配模板函数时,不进行类型自动转换

template<class T>
T myFunction( T arg1, T arg2)
{ cout<<arg1<<" "<<arg2<<"\n"; return arg1;}
……
myFunction( 5, 7);      //ok :replace T with int
myFunction( 5.8, 8.4);  //ok: : replace T with double
myFunction( 5, 8.4);    //error ,no matching function for callto &#39;myFunction(int, double)&#39;

二、类模板

1、定义

     在定义类的时候,加上一个/多个类型参数。在使用类模板时,指定类型参数应该如何替换成具体类型,编译器据此生成相应的模板类。

    template 8723d48d3da68ef76dc4da900401e53a //类型参数表
    class 类模板名{
           成员函数和成员变量
    };

(1)类模板里成员函数的写法:
        template 8723d48d3da68ef76dc4da900401e53a //类型参数表
        返回值类型 类模板名3be254a78ac4ef5d0275e4f498aef232::成员函数名(参数表){
             ……
        }
(2)用类模板定义对象的写法:
         类模板名 7e514a50f88abc3ec910af0085680e97 对象名(构造函数实参表);

// Pair类模板
template <class T1,class T2>
class Pair{
public:
    T1 key; //关键字
    T2 value; //值
    Pair(T1 k,T2 v):key(k),value(v) { };
    bool operator < ( const Pair<T1,T2> & p) const;
};
template<class T1,class T2>
bool Pair<T1,T2>::operator < ( const Pair<T1,T2> & p) const{  //Pair的成员函数 operator <
    return key < p.key;
}
int main(){
    Pair<string,int> student("Tom",19);   //实例化出一个类 Pair<string,int>
    cout << student.key << " " << student.value;
    return 0;
}
//输出:
Tom 19

2、用类模板定义对象

  • 编译器由类模板生成类的过程叫类模板的实例化。由类模板实例化得到的类,叫模板类。

  • 同一个类模板的两个模板类是不兼容的。

3、函数模版作为类模板成员

template <class T>
class A{
    public:
        template<class T2>
        void Func( T2 t) { cout << t; } //成员函数模板
};

4、类模板与非类型参数:类模板的“aeb076f2de6d9fd925f87f01d34d7038”中可以出现非类型参数

template <class T, int size>
class CArray{
    T array[size];
public:
    void Print(){
        for( int i = 0;i < size; ++i)
        cout << array[i] << endl;
    }
};
CArray<double,40> a2;
CArray<int,50> a3;     //a2和a3属于不同的类

5、类模板与派生

(1)类模板从类模板派生

template <class T1,class T2>              int main() {
class A {                                        B<int,double> obj1;
    T1 v1; T2 v2;                                C<int> obj2;
};                                               return 0;
template <class T1,class T2>              }
class B:public A<T2,T1> {                 class B<int,double>:
    T1 v3; T2 v4;                             public A<double,int>{
};                                            int v3; double v4;
template <class T>                        };
class C:public B<T,T> {
    T v5;
};

(2)类模板从模板类派生

template <class T1,class T2>
class A {
    T1 v1; T2 v2;
};
template <class T>
class B:public A<int,double> {
    T v;
};
int main() {
    B<char> obj1;     //自动生成两个模板类 :A<int,double> 和 B<char>
    return 0;
}

(3)类模板从普通类派生

class A {
    int v1;
};
template <class T>
    class B:public A { //所有从B实例化得到的类 ,都以A为基类
    T v;
};
int main() {
    B<char> obj1;
    return 0;
}

(4)普通类从模板类派生

template <class T>
class A {
    T v1;
    int n;
};
class B:public A<int> {
    double v;
};
int main() {
    B obj1;
    return 0;
}

6、类模板与友员函数
(1)函数、类、类的成员函数作为类模板的友元

void Func1() { }
class A { };
class B{
    public:
        void Func() { }
};
template <class T>
class Tmpl{
    friend void Func1();
    friend class A;
    friend void B::Func();
}; //任何从Tmp1实例化来的类 ,都有以上三个友元

(2)函数模板作为类模板的友元

#include <iostream>
#include <string>
using namespace std;
template <class T1,class T2>
class Pair{
    private:
        T1 key; //关键字
        T2 value; //值
    public:
        Pair(T1 k,T2 v):key(k),value(v) { };
        bool operator < ( const Pair<T1,T2> & p) const;
        template <class T3,class T4>
        friend ostream & operator<< ( ostream & o,const Pair<T3,T4> & p);
};
template <class T1,class T2>
bool Pair<T1,T2>::operator < ( const Pair<T1,T2> & p) const{ //"小"的意思就是关键字小
    return key < p.key;
}
template <class T1,class T2>
ostream & operator<< (ostream & o,const Pair<T1,T2> & p){
    o << "(" << p.key << "," << p.value << ")" ;
    return o;
}
int main()
{
    Pair<string,int> student("Tom",29);
    Pair<int,double> obj(12,3.14);
    cout << student << " " << obj;
    return 0;
}
//输出:
(Tom,29) (12,3.14)
任意从 template <class T1,class T2>
       ostream & operator<< (ostream & o,const Pair<T1,T2> & p)
生成的函数,都是任意Pair摸板类的友元

(3)函数模板作为类的友元

#include <iostream>
using namespace std;
class A
{
    int v;
public:
    A(int n):v(n) { }
    template <class T>
    friend void Print(const T & p);
};
template <class T>
void Print(const T & p){
    cout << p.v;
}
int main() {
    A a(4);
    Print(a);
    return 0;
}
//输出:4

(4)类模板作为类模板的友元

template <class T>
class B {
    T v;
public:
    B(T n):v(n) { }
    template <class T2>
    friend class A;
};
template <class T>
class A {
    public:
    void Func( )  {
        B<int> o(10);
        cout << o.v << endl;
    }
};

7、类模板与静态成员变量

     类模板中可以定义静态成员 ,那么从该类模板实例化得到的所有类 ,都包含同样的静态成员 。

#include <iostream>
using namespace std;
template <class T>
class A{
    private:
        static int count;
    public:
        A() { count ++; }
        ~A() { count -- ; };
        A( A & ) { count ++ ; }
        static void PrintCount() { cout << count << endl; }
};
template<> int A<int>::count = 0;
template<> int A<double>::count = 0;
int main(){
    A<int> ia;
    A<double> da;
    ia.PrintCount();
    da.PrintCount();
    return 0;
}
//输出:1  1

相关推荐:

用C++对C++语法格式进行分析

c++11 - C++中如何定义一个指向函数的智能指针?

以上是深度解析C++的函数模板与类模板的详细内容。更多信息请关注PHP中文网其他相关文章!

声明
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
C#.NET用于网络,桌面和移动开发C#.NET用于网络,桌面和移动开发Apr 25, 2025 am 12:01 AM

C#和.NET适用于Web、桌面和移动开发。1)在Web开发中,ASP.NETCore支持跨平台开发。2)桌面开发使用WPF和WinForms,适用于不同需求。3)移动开发通过Xamarin实现跨平台应用。

C#.NET生态系统:框架,库和工具C#.NET生态系统:框架,库和工具Apr 24, 2025 am 12:02 AM

C#.NET生态系统提供了丰富的框架和库,帮助开发者高效构建应用。1.ASP.NETCore用于构建高性能Web应用,2.EntityFrameworkCore用于数据库操作。通过理解这些工具的使用和最佳实践,开发者可以提高应用的质量和性能。

将C#.NET应用程序部署到Azure/AWS:逐步指南将C#.NET应用程序部署到Azure/AWS:逐步指南Apr 23, 2025 am 12:06 AM

如何将C#.NET应用部署到Azure或AWS?答案是使用AzureAppService和AWSElasticBeanstalk。1.在Azure上,使用AzureAppService和AzurePipelines自动化部署。2.在AWS上,使用AmazonElasticBeanstalk和AWSLambda实现部署和无服务器计算。

C#.NET:强大的编程语言简介C#.NET:强大的编程语言简介Apr 22, 2025 am 12:04 AM

C#和.NET的结合为开发者提供了强大的编程环境。1)C#支持多态性和异步编程,2).NET提供跨平台能力和并发处理机制,这使得它们在桌面、Web和移动应用开发中广泛应用。

.NET框架与C#:解码术语.NET框架与C#:解码术语Apr 21, 2025 am 12:05 AM

.NETFramework是一个软件框架,C#是一种编程语言。1..NETFramework提供库和服务,支持桌面、Web和移动应用开发。2.C#设计用于.NETFramework,支持现代编程功能。3..NETFramework通过CLR管理代码执行,C#代码编译成IL后由CLR运行。4.使用.NETFramework可快速开发应用,C#提供如LINQ的高级功能。5.常见错误包括类型转换和异步编程死锁,调试需用VisualStudio工具。

揭开c#.net的神秘面纱:初学者的概述揭开c#.net的神秘面纱:初学者的概述Apr 20, 2025 am 12:11 AM

C#是一种由微软开发的现代、面向对象的编程语言,.NET是微软提供的开发框架。C#结合了C 的性能和Java的简洁性,适用于构建各种应用程序。.NET框架支持多种语言,提供垃圾回收机制,简化内存管理。

C#和.NET运行时:它们如何一起工作C#和.NET运行时:它们如何一起工作Apr 19, 2025 am 12:04 AM

C#和.NET运行时紧密合作,赋予开发者高效、强大且跨平台的开发能力。1)C#是一种类型安全且面向对象的编程语言,旨在与.NET框架无缝集成。2).NET运行时管理C#代码的执行,提供垃圾回收、类型安全等服务,确保高效和跨平台运行。

C#.NET开发:入门的初学者指南C#.NET开发:入门的初学者指南Apr 18, 2025 am 12:17 AM

要开始C#.NET开发,你需要:1.了解C#的基础知识和.NET框架的核心概念;2.掌握变量、数据类型、控制结构、函数和类的基本概念;3.学习C#的高级特性,如LINQ和异步编程;4.熟悉常见错误的调试技巧和性能优化方法。通过这些步骤,你可以逐步深入C#.NET的世界,并编写高效的应用程序。

See all articles

热AI工具

Undresser.AI Undress

Undresser.AI Undress

人工智能驱动的应用程序,用于创建逼真的裸体照片

AI Clothes Remover

AI Clothes Remover

用于从照片中去除衣服的在线人工智能工具。

Undress AI Tool

Undress AI Tool

免费脱衣服图片

Clothoff.io

Clothoff.io

AI脱衣机

Video Face Swap

Video Face Swap

使用我们完全免费的人工智能换脸工具轻松在任何视频中换脸!

热工具

PhpStorm Mac 版本

PhpStorm Mac 版本

最新(2018.2.1 )专业的PHP集成开发工具

记事本++7.3.1

记事本++7.3.1

好用且免费的代码编辑器

SublimeText3 Linux新版

SublimeText3 Linux新版

SublimeText3 Linux最新版

mPDF

mPDF

mPDF是一个PHP库,可以从UTF-8编码的HTML生成PDF文件。原作者Ian Back编写mPDF以从他的网站上“即时”输出PDF文件,并处理不同的语言。与原始脚本如HTML2FPDF相比,它的速度较慢,并且在使用Unicode字体时生成的文件较大,但支持CSS样式等,并进行了大量增强。支持几乎所有语言,包括RTL(阿拉伯语和希伯来语)和CJK(中日韩)。支持嵌套的块级元素(如P、DIV),

适用于 Eclipse 的 SAP NetWeaver 服务器适配器

适用于 Eclipse 的 SAP NetWeaver 服务器适配器

将Eclipse与SAP NetWeaver应用服务器集成。