1、友元函数与模板类
常见类型
模板函数中,实现友元函数,大概有下面几种分类。
- 不需要模板参数的非模板函数
- 需要模板参数的非模板函数
- 需要模板参数的模板函数,使用类的模板参数来特化
- 需要模板参数的模板函数,使用自己的模板参数。(可以有多个模板参数)
template<typename T>
class A;
template<typename T>
void func3(const A<T>& obj);
template<typename T>
class A {
public:
A(T data) : ma(data) {}
friend void func1();
friend void func2(const A<T>& obj) {
cout << obj.ma << endl;
}
friend void func3<>(const A<T>& obj);
template<typename U>
friend void func4(const A<U>& obj);
private:
T ma;
static T num;
};
template<typename T>
T A<T>::num = 10.5;
void func1() {
cout << A<int>::num << endl;
}
template<typename T>
void func3(const A<T>& obj) {
cout << obj.ma << endl;
cout << A<T>::num << endl;
}
template<typename U>
void func4(const A<U>& obj) {
cout << obj.ma << endl;
}
几点说明
1、func2,在类内定义的话,会自动生成对应的函数。如果在类外定义的话,只能为每一种参数都特化一个函数。
void fun2(const A<int>& obj) {
cout << obj.ma << endl;
}
void func2(const A<float>& obj) {
cout << obj.ma << endl;
}
.......
2、func3,在类外定义的话,不需要像func2一样,每种参数类型都特化一个函数。在类内定义的话,需要加上 关键字。注意func3这种类型,需要在提前声明。
template<typename T>
class A {
public:
....
template<typename T>
friend void func3<>(const A<T>& obj) {
cout << obj.ma << endl;
}
....
private:
T ma;
static T num;
};
3、func2 不需要模板参数推导,相比 func3 是更优的匹配,两者同名时会优先调用 func2。
4、func3 和 func4 的区别在于:func3 是模板类实例化一个参数后,func3也实例化一个。func4 所有类型的函数,都是模板一个实例化的友元。func3 属于一对一。func4 属于 多对一。
template <typename T>
void func3(const A<T> &a)
{
cout << "f3: " << A<double>::num << endl;
}
template <typename U>
void func4(const A<U> &a)
{
cout << "f4: " << A<double>::num << endl;
}
A<int> a(10);
func3(a); 会报错
func4(a); 可以调用。
func4 对于 A<int> 可以有多个实例,func3 只有 int。
?参考:? https://www.cnblogs.com/h-hg/p/8783935.html
2、模板类与模板类
1、模板类作为另一个模板类的成员变量。公用一个T
一般情况下,类去做成员变量的时候,都会以指针的形式去声明定义。同时,也不能忘记模板参数,或者直接实例化。
template<typename T>
class A {
public:
A(T data) : ma(data) {}
void print() {
cout << ma << endl;
}
private:
T ma;
};
template<typename T>
class B {
public:
B(T data) : mb(data) {
pa = new A<T>(data);
}
void print() {
pa->print();
}
~B() {
delete pa;
}
private:
T mb;
A<T>* pa;
};
int main()
{
B<int> b(10);
b.print();
return 0;
}
###也可以这样写
template<typename T, typename Ac = A<T>>
class B {
public:
B(T data) : mb(data) {
pa = new Ac(data);
}
void print() {
pa->print();
}
~B() {
delete pa;
}
private:
T mb;
Ac* pa;
};
2、C++类模板与继承
。。。
|