类模板和函数模板引发的思考

   首先我们在学习类模板和函数模板时候会遇到这样一个问题:

  类模板 与模板类

 函数模板与模板函数

这些不仅仅是简单的文字游戏,而是需要我们深深的区分一下才可以理解其中的奥秘!

再回想一下我们在学习C语言的时候也遇到了这样几个类似的名词

函数指针与指针函数

数组指针与指针数组

函数指针即是重点在后边的名词指针,前边的函数只是修饰名词指针的一个定语而已,欧,这是一个语文的奥秘哟,忽然觉得自己好博学,言归正传,重点在指针,那就是指向一个函数的指针,其中保存了这个函数的地址通过指针解引用可以调用这个函数 就是这个形式 int(*p)()=fun;这里的fun是函数名。

指针函数,重点还是在函数这个名词之上,首先是一个函数,用指针修饰这个函数,就是指的是函数的返回值是一个指针 就是这个形式 int * fun();

数组指针,同理是一个指针,只是这个指针指向的是一个数组整体而已  形式是 int(*p)[4]=a;a是数组的名字,指针中的4表示指针的步长,如果是个二维数组最好数组的行数与4相同,这里不再深究

指针数组  重点在数组,就是一个数组中存储的全是指针,这时候该明白了吧!

下来说类模板和模板类

类模板的重点是模板。表示的是一个模板,专门用于产生类的模子。例子:
template   <typename   T>

class   Vector

{
 …
};

使用这个Vector模板就可以产生很多的class(类),Vector <int> 、Vector <char>

模板类的重点是类。表示的是由一个模板生成而来的类。例子:

上面的Vector <int> 、Vector <char> 、……全是模板类。


模板类的重点是类。表示的是由一个模板生成而来的类。例子:

上面的Vector <int> 、Vector <char> 、……全是模板类。


并且类模板的定义与声明不能跨文件就是在.h文件中声明的模板类必须也在.h中定义类模板,因为在生成模板类的时候类模板必须找到定义才能生成

以下是书中的一些英文原意:
In   order   for   the   compiler   to   generate   the   code,   it   must   see   both   the   template   definition   (not   just   declaration)   and   the   specific   types/whatever   used   to   "fill   in "   the   template.   For   example,   if   you 're   trying   to   use   a   Foo <int> ,   the   compiler   must   see   both   the   Foo   template   and   the   fact   that   you 're   trying   to   make   a   specific   Foo <int> 。

下来说函数模板和模板函数

函数模板的重点是模板。表示的是一个模板,专门用来生产函数。例子:

template   <typename   T>

void   fun(T   a)

{

            …

}

在运用的时候,可以显式(explicitly)生产模板函数,fun <int> 、fun <double> 、fun <Shape*> ……。

也可以在使用的过程中由编译器进行模板参数推导,帮你隐式(implicitly)生成。

fun(8);//隐式生成fun <int>   显示生成使用 fun<int>(8);以下雷同

fun(9.9);//隐式生成fun <double>

fun(‘a’);//   隐式生成fun <char>

Shape*   ps   =   new   Cirlcle;

fun(ps);//隐式生成fun <Shape*>

模板函数的重点是函数。表示的是由一个模板生成而来的函数。例子:

上面显式(explicitly)或者隐式(implicitly)生成的fun <int> 、fun <Shape*> ……都是模板函数。
以下是类模板和模板类 函数模板和模板函数的简单实现

/**********************************************************************     
* *   Copyright (c)2015,WK Studios   
* *   Filename:  A.h 
* *   Compiler: GCC  vc 6.0    
* *   Author:WK     
* *   Time: 2015 24 6  
* **********************************************************************/  

#include <iostream>
using namespace std;
//类模板
template<typename B=int>
class S
{
	public:
		S(B n=0):m_data(n)
		{

		}
		void Modif(B n);
        void show()
		{
			cout<<m_data<<"\n";
		}

	private:
     B m_data;
};

//函数模板
template <typename T=int>
T Max(T a,T b)
{
	return a>b?a:b;
}
template <typename T1,typename T2>
T1 Min(T1 a, T2 b)
{
	return a<b?a:b;
}
//多个参数类型的模板类
template <typename A1=int,typename A2>
class A
{
	public:
	A(A1 a,A2 b):m_data(a),data(b)
	{

	}
	void Modif(A1 ,A2);
	void show()
	{
	cout<<m_data<<"\n";
	cout<<data<<"\n";
		
	}
	private:
		A1 m_data;
		A2 data;

};
int fun()
{
	return 0;
}


int main()

{ int (*p)()=fun;
	
	cout<<"------类模板---------\n";
	S<int> s1(5),s2(6);
	S <>s3(8.8);//调用缺省的类模板
    s1.show();
	s2.show();
    s3.show();
	s1.Modif(2);
	s1.show();

   A<int,int>a1(2,3);
   a1.show();
   a1.Modif(9,9);
   a1.show();

   cout<<"------函数模板--------\n";
   cout<<Max(4,static_cast <int>(9.2))<<"\n";
   cout<<Max<double>(4,8.3)<<"\n";

  
   cout<<Min(4,8.3)<<"\n";//这里返回值是其中一个参数的类型,但是如果结果返回值是另一个参数的类型,那莫就要进行隐式的类型转换,C++倒是没有提供智能的选择类型的功能
	return 0;
}

template <typename B>
void S<B>::Modif(B n)//类外部实现对象
{
	m_data=n;
}

template <typename A1,typename A2>
void A<A1,A2>::Modif(A1 a,A2 b)//类外部实现对象
{
	m_data=a;
	data=b;
}



#include <iostream>
using namespace std;

template <typename T,typename T1,typename T2>
T Max(T1 a,T2 b)
{
	return a>b?a:b;
}


int main()

{ 
	//可以显式的指定返回值
  cout<<Max<double>(4,8.3)<<"\n"; 
  cout<<Max<int>(9,8.3)<<"\n";
}




评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值