博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
C++ Primer Plus 学习笔记 成员模板 模板用作参数 模板友元 模板别名
阅读量:4127 次
发布时间:2019-05-25

本文共 5694 字,大约阅读时间需要 18 分钟。

意思就是类模板中吧类模板当做成员函数或者类成员

直接上代码吧

#include 
using std::cout;using std::cin;using std::endl;template
class beta{ private: template
class hold { private: V val; public: shold(V v = 0) : val(v) {} void show() const {cout << val << endl;} V Value() const {return val;} }; hold
q; hold
n; public: beta(T t, int i) : q(t), n(i) {} template
U blab(U u, T t){return (n.Value() + q.Value()) * u /t;} void Show() const { q.show(); n.show();}};int main(){ beta
guy(3.5, 3); cout << "T was set to double\n"; guy.Show(); cout << "V was set to T, which is double, then V was set to int\n"; cout << guy.blab(10, 2.3) << endl; cout << "U was set to int\n"; cout << guy.blab(10.0, 2.3) << endl; cout << "U was set to double\n"; cout << "Done\n"; return 0;}

C++允许外部定义成员模板。但不是所有的编译器都支持。 如果不支持的话就算了 支持的话可以这么写:

将模板用于参数:

先上代码在说话

stacktp.h

#ifndef STACKTP_H_#define STACKTP_H_template
class Stack{ private: enum {MAX = 10}; Type items[MAX]; int top; public: Stack(); bool isempty(); bool isfull(); bool push(const Type & item); bool pop(Type & item);};template
Stack
::Stack(){ top = 0;}template
bool Stack
::isempty(){ return top == 0;}template
bool Stack
::isfull(){ return top == MAX;}template
bool Stack
::push(const Type & item){ if (top < MAX) { items[top++] = item; return true; } else { return false; }}template
bool Stack
::pop(Type & item){ if (top > 0) { item = items[--top]; return true; } else return false;}#endif

tempparm.cpp

#include 
#include "stacktp.h"template

运行结果:

模板类和友元:

模板类可以有友元, 但是有3种友元

1. 非模板友元

2. 约束模板友元

3.非约束模板友元

 

一个一个来

非模板友元

template 
class A{ public: friend void counts();}

counts()是模板所有实例化对象的友元。 这是不带参数的例子。它可以访问全局对象,可以使用全局指针访问的费全局对象。可以创建自己的对象。 可以访问独立于对象的模板类的静态数据成员。

那如果要带参数呢  而且是要带模板类参数呢?

但需要指明特定类型的对象 比如:

template 
class A{ public: friend void counts(A
&);}

这样将counts将称为A<T>类的友元。

程序示例:

#include 
using std::cout;using std::endl;template
class HasFriend{ private: T item; static int ct; public: HasFriend(const T & i) : item(i) {ct++;} ~HasFriend() {ct--;} friend void counts(); friend void reports(HasFriend
&);};template
int HasFriend
::ct = 0;void counts(){ cout << "int count: " << HasFriend
::ct << "; "; cout << "double count: " << HasFriend
::ct << endl;}void reports(HasFriend
& hf){ cout << "HasFriend
: " << hf.item << endl;}void reports(HasFriend
& hf){ cout << "HasFriend
: " << hf.item << endl;}int main(){ cout << "No objects delared: "; counts(); HasFriend
hfi1(10); cout << "After hfil declared: "; counts(); HasFriend
hfi2(20); cout << "After hfi2 declared: "; counts(); HasFriend
hfdb(10.5); cout << "AFter hfdb delared: "; counts(); reports(hfi1); reports(hfi2); reports(hfdb); return 0;}

运行结果

2.约束模板友元函数

就是把友元函数先声明为函数模板 然后在类模板中定义的是该函数模板

程序示例:

#include 
using std::cout;using std::endl;template
void counts();template
void report(T &);template
class HasFriendT{ private: TT item; static int ct; public: HasFriendT(const TT & i) : item(i) {ct++;} ~HasFriendT() {ct--;} friend void counts
(); friend void report<>(HasFriendT &);};template
int HasFriendT
::ct = 0;template
void counts(){ cout << "template size: " << sizeof(HasFriendT
) << "; "; cout << "template counts(); " << HasFriendT
::ct << endl;}template
void report(T & hf){ cout << hf.item << endl;}int main(){ counts
(); HasFriendT
hfi1(10); HasFriendT
hfi2(20); HasFriendT
hfdb(10.5); report(hfi1); report(hfi2); report(hfdb); cout << "counts
() output:\n"; counts
(); cout << "counts
() output:\n"; counts
(); return 0;}

运行结果

3.非约束模板友元函数

模板类型放开 ,不用跟着模板类型走:

示例:

#include 
using std::cout;using std::cin;template
class ManyFriend{ private: T item; public: ManyFriend(const T & i) : item(i) {} template
friend void show2(C &, D &);};template
void show2(C & c, D & d){ cout << c.item << ", " << d.item << '\n';}int main(){ ManyFriend
hfi1(10); ManyFriend
hfi2(20); ManyFriend
hfdb(10.5); cout << "hfi1, hfi2: "; show2(hfi1, hfi2); cout << "hfdb, hfi2: "; show2(hfdb, hfi2); return 0;}

运行结果

大体区别就是

非模板的友元: 没有跟着哪个类 就是跟某个实例对象友元。

约束模板函数: 就是跟某个类型的模板关联。 

非约束模板函数: 不限制某个类型的模板, 因为定义了另外的两个模板参数。所以可以传入不同类型的模板作为参数。

然后目前来说。好像没啥卵用。

模板别名:

可以这样定义别名:

typedef std::array
arri;

C++11 可以这样:

template<typename T> 

using arrtype = std::array<T, 12>;

然后可以这么干:

arrtype<double> gallons;

arrtype<int> days;   == array<int , 12>

这种定义别名的方式也适用于非模板

优点: 可读性更强,因为它让类型名和类型信息更清晰。

总结:

第十四章 真 •  完结

转载地址:http://gnepi.baihongyu.com/

你可能感兴趣的文章
EntityFramework 学习之一 —— 模型概述与环境搭建 .
查看>>
C# 发HTTP请求
查看>>
启动 LocalDB 和连接到 LocalDB
查看>>
Palindrome Number --回文整数
查看>>
Reverse Integer--反转整数
查看>>
Container With Most Water --装最多水的容器(重)
查看>>
Longest Common Prefix -最长公共前缀
查看>>
Letter Combinations of a Phone Number
查看>>
Single Number II --出现一次的数(重)
查看>>
Valid Parentheses --括号匹配
查看>>
Remove Element--原地移除重复元素
查看>>
Remove Duplicates from Sorted Array--从有序数组中移除重复元素
查看>>
Count and Say
查看>>
Gas Station
查看>>
Palindrome Partitioning --回文切割 深搜(重重)
查看>>
Valid Palindrome 简单的回文判断
查看>>
Pascal's Triangle -- 生成杨辉三角
查看>>
Pascal's Triangle II 生成杨辉三角中的某行
查看>>
Minimum Depth of Binary Tree -- 二叉树的最小深度 DFS 加剪枝
查看>>
Climbing Stairs 爬楼梯方法 动态规划
查看>>