十年网站开发经验 + 多家企业客户 + 靠谱的建站团队
量身定制 + 运营维护+专业推广+无忧售后,网站问题一站解决
那是C++自带的模板库,C的很少,而且代码长难记且功能少,基本可以忽略。
为惠山等地区用户提供了全套网页设计制作服务,及惠山网站建设行业解决方案。主营业务为成都做网站、成都网站设计、惠山网站设计,以传统方式定制建设网站,并提供域名空间备案等一条龙服务,秉承以专业、用心的态度为用户提供真诚的服务。我们深信只要达到每一位用户的要求,就会得到认可,从而选择与我们长期合作。这样,我们也可以走得更远!
要是用C的话,函数基本要自己写的
各种用
C
语言实现的模板可能在使用形式上有所不同。现以一个求和函数
Sum
为例,用
C++
Template
可写如下:
template
R
Sum(const
T
*array,
int
n)
{
R
sum
=
0;
for
(int
i
=
;
i
n
;
++i)
sum
+=
i;
return
sum;
}
如果不是内置类型,该模板隐式地需要
有R
R::operator+=(T)运算符可用。
1.
使用函数指针作为
Functor
替换者
Typedef
struct
tagAddClass
{
Void
(*add)(char*
r1,
const
char*
r2);
Int
elemSize;
Char
sum[MAX_ELEM_SIZE];
}
AddClass;
void
Sum(AddClass*
self,
const
char*
array,
int
n)
{
for
(int
i
=
;
i
n
;
++i)
self-add(self-sum,
array
+
i*self-elemSize);
}
使用时:
Void
AddInt(char*
r1,
const
char*
r2)
{
*(long*)r1
+=
*(int*)r2;
}
AddClass
addClass
=
{AddInt,
2,
};
Int
array[100];
Read(array);
Sum(addClass,
array,
100);
…..
2.
用宏作为Functor的替换者
#define
GenSumFun(SumFunName,
Add,
RetType,
ElemType)
RetType
SumFunName
(const
ElemType
*array,
int
n)
\
{
RetType
sum
=
0;
for
(int
i
=
;
i
n
;
++i)
Add(sum,
i);
return
sum;
}
使用时:
#define
AddInt(x,
y)
((x)
+=
(y))
GenSumFun(SumInt,
AddInt,
long,
int)
…..
Int
array[100];
Read(array);
Long
sum
=
SumInt(array,
100);
…..
3.
所有可替换参数均为宏
至少需要一个额外的文件(实现文件)为
impsum.c
/*
impsum.c
*/
RetType
FunName(const
ElemType
*array,
int
n)
{
RetType
sum
=
0;
for
(int
i
=
;
i
n
;
++i)
Add(sum,
i);
return
sum;
}
使用时:
#undef
RetType
#undef
FunName
#undef
ElemType
#undef
Add
#define
AddInt(x,
y)
((x)
+=
(y))
#define
RetType
long
#define
FunName
SumInt
#define
ElemType
int
#define
Add
AddInt
#include
impsum.c
…..
Int
array[100];
Read(array);
Long
sum
=
SumInt(array,
100);
4.
总结:
第一种方法,易于跟踪调试,但是效率低下,适用于对可变函数(函数指针)的效率要求不高,但程序出错的可能性较大(复杂),模板函数(Sum)本身很复杂,模板参数也比较复杂(add)的场合。
第二种方法,效率高,但很难跟踪调试,在模板函数和模板参数本身都很复杂的时候更是如此。
第三种方法,是我最近几天才想出的,我认为是最好的,在模板参数(Add)比较复杂时可以用函数(第二种也可以如此),简单时可以用宏,并且,易于调试。在模板函数本身很复杂,而模板参数比较简单时更为优越。但是,可能有点繁琐。
这些都是C++的玩意
T min( T (arr)[size] ); //T (arr)[size] arr是个数组的引用, 如果去掉括号,就变成引用的数组,而引用的数组是不存在的,改成T*就成了第二种定义了
用引用当参数,比如min(a),a就是实参本身,而不是副本,这是C语言所没有的特性. 既然是实参本身,那么数组a就不会退化为指针,也就是说,编译器可以可以获得a的大小,所以size就不需要提供了
而第一种和第二种,arr退化为指针了,所以必须通过其他途径提供数组长度,
首先,C没有函数模版。C++才有。
其次,template class T是函数声明的一部分,所以下面函数实现应该是:
template class T
void swap(T a,T b){
int temp;
temp=a;
a=b;
b=temp;
}
最后,#include iostream,在标准的C++函数中,std的域中已经有一个swap函数。
而且前面也using namespace了。函数声明重复。
两个办法:
1 swap(i,j);改为 ::swap(i,j); //全局化。
2 swap改个名字。
代码如下:
#include iostream
using namespace std;
// 加法的模板函数
template typename T
T Add(T a, T b)
{
return (a + b);
}
// 测试函数
int main()
{
// 显式
cout"显式调用:"endl;
int ia = 1, ib = 2, ic = 0;
ic = Addint(ia, ib);
coutia" + "ib" = "icendl;
// 隐式
cout"隐式调用:"endl;
float fa = 1.1f, fb = 2.2f, fc = 0.0f;
fc = Add(fa, fb);
coutfa" + "fb" = "fcendl;
coutendl;
return 0;
}
测试结果: