【语法】模板
来源:互联网 发布:资历章排列软件 编辑:程序博客网 时间:2024/05/12 13:22
- 泛型代码两个原则:
1 模板中函数参数是const的引用:保证函数可用于不能拷贝的类型
2 函数体只是用<比较运算
- 类型模板参数:
template<typename T> inline bool compare(const T& lhs, const T& rhs){ return lhs < rhs;}
- 非类型模板参数:
template<unsigned N> inline int back(const int (&lhs)[N]){ return lhs[N - 1];}int main(){ const int a[2]{1, 2}; cout<<back(a); return 0;}
1 数组作为非引用参数会被退化为指针,无法推导出N,需要使用引用保持数组类型
注意区别引用的数组:
bool back(int &lhs[2])
//非法
和数组的引用:
bool back(int (&lhs)[2])
2 inline说明符放在模板参数列表之后
- 模板编译:
编译器遇到模板定义时,并不生成代码。只有当实例化出模板的特定版本时,编译器才会生成代码,为了生成一个实例化版本,编译器需要掌握函数模板或类模板的成员函数的定义。因此,模板的头文件包含声明和定义。函数模板和类模板的成员函数定义放在头文件中。
- 类模板
函数模板可以推导参数类型,类模板不可以,需要额外提供信息
template<typename T> class Blob{private: vector<T> vec;public: void func(const T& lhs);};template<typename T> void Blob<T>::func(const T& lhs){ vec.push_back(lhs);}int main(){ Blob<int> b; b.func(2); return 0;}
使用类模板类型时必须提供模板参数,
在类模板自己的作用域中,可以直接使用模板名而不提供实参,
在类外定义成员时,直到遇到类名::才算进入类作用域
template<typename T>Blob<T> Blob<T>::operator++(int lhs){ Blob ret = *this; return ret;}
- 使用类的类型成员
默认情况下,作用域运算符访问的是名字,不是类型。使用typename显示告诉编译器访问的是类型。
template <typename T>typename T::value_type top(const T& c){ return typename T::value_type();}
- 模板成员函数:
模板成员函数不能是虚函数
template<typename T>template<typename It>Blob <T>::Blob(It b, It e){ vec.insert(vec.begin(), b, e);}
类模板外定义成员模板函数时,必须同时为类和成员模板提供模板参数列表,编译器根据实参推断模板成员函数的参数类型。
- 控制实例化
当两个或者多个独立编译的源文件使用了相同的模板,并提供了相同的模板参数,每个文件都会有改模板的一个实例。
通过显示的实例化避免开销
A文件:
extern template class Blob<string>; //实例化声明Blob<string> s1;//实例化在其他文件
B文件:
template class Blob<sting>;//实例化定义
将一个实例化声明为extern就表示承诺在程序的其他位置有该实例化的非extern声明(定义)。
与普通实例化不同,实例化定义会实例化所有成员。
普通情况下,类模板的成员函数只有当程序用到它时才会实例化。
- 函数模板显式实参
template<typename T1,typename T2,typename T3>T1 sum(T2, T3);auto func = sum<long>(i,j)
特别是当返回类型与函数参数列表中的所有类型不一致时,需要显式指出返回类型。
为了不显式实参,可以使用尾置返回类型
template<typename It>auto func(It begin, It end)->decltype(*begin){ return *begin;}
解引用返回左值,decltype推断的类型为begin所指元素类型的引用
若只要返回值,不返回引用,可使用类型转换模板进行类型转换
- 模板语法
- 【语法】模板
- 模板语法
- StringTemplate.net模板语法
- C++语法 模板 (转)
- 模板标签语法简介
- 模板语法<精通篇>
- Briage 模板语法
- Cmake 模板和语法
- 【discuz】discuz模板语法
- 【discuz】discuz模板语法
- destoon 模板语法
- Discuz!模板解析语法
- velocity模板常用语法
- Cmake 模板和语法
- Play framework模板语法
- Angular 2模板语法
- 模板中的语法知识
- 19 个 JavaScript 常用的简写技术
- 如何下载POI标注-信息点
- OpenCV之RNG生成随机数类详解
- 无法为更新定位行,一些值可能已在最后一次读取后已更改
- 子类继承父类时,super的初始化位置
- 【语法】模板
- jQuery事件委派实例(双击删除图片和对应隐藏域)
- 面向对象--绑定方法与非绑定方法
- spring mvc 启动过程
- 一个女孩子四年同居后还剩下什么
- Unity3D编辑器之自定义窗口显示文件夹结构
- 项目管理工具禅道使用教程(简介,说明,邮箱设置)
- LeetCode: 606. Construct String from Binary Tree
- java junit