总结:C++中的类型推导

来源:互联网 发布:航天发票数据管理软件 编辑:程序博客网 时间:2024/06/06 23:45

# 总结:C++中的类型推导
使用c++的过程中,与类型推导直接相关的两种情况是templateauto(c++11),两者的类型推导规则仅有细微不同。

1. template

template 的类型推导可分为三种情况:

1.1. 参数是引用或指针,但不是universal reference

当参数是引用时,理解上可以按照这样的顺序进行类型推导:形参的类型是以实参类型为基础的,通过形参的形式即可得出使模板具现化的类型。
注:1、实际上的顺序是相反顺序的。 2、“为基础”是指不完全相同,还需考虑形参的形式,可能会加上引用/const /volatile

template<typename T> void f(T &param);  // 指针的情况与引用相似const int cx = 27;f(cx);  // param的类型是const int&,形参比实参多加上引用,T是const intconst int &rx = cx;f(rx);  // param的类型是const int&, T是const inttemplate<typename T> void cf(const T &param);int x = cx;cf(x);  // param的类型是const int&, 形参比实参多加上了const, T是int

当参数是指针时,与上述规则类似。

1.2. 参数是通用引用(C++11)

通用引用的情况和参数是引用的情况基本相同,唯一的差别是当参数是通用引用的时候,在“由形参的形式得出使模板具现化的类型”的过程中要考虑引用折叠(C++11)

template<typename T> void f(T &&param);int lx = 27;  // 左值f(lx);  // param是int&, 使用引用折叠,T是int&const int &lrx = lx;  // 左值f(lrx);  // param是const int&, 使用引用折叠, T是const int&int &&rrx = 27;  // 右值f(rrx);  // param是int&&, T是int

1.3. 参数既不是指针也不是引用时

当参数既不是指针也不是引用时,形参的类型是以实参类型为基础的,会去除引用/const /volatile,通过形参的形式即可得出使模板具现化的类型。

template<typename T> void f(T param);const int cx = 27;f(cx);  // param是int, 形参比实参少了const, T是intconst int &rcx = cx;f(rcx);  // param是int, 形参比实参少了const和引用, T是inttempalte<typename T> void cf(const T param);int x = 27;int &rx = x;cf(rx);  // param是const int, 形参比实参多了const少了引用, T是int

2.auto

C++11中autotemplate 的类型推导仅在使用了{ } 的时候有所不同:
  auto 能为{ } 推导出std::initializer_list<T> template 则无法推导类型。

在C++14中,还有一点值得注意:
  auto 应用在返回类型和lambda 表达式的参数时,使用的是template 的类型推导规则。

auto f() { return { 1, 2, 3 }; }  // error: 无法推导{ 1, 2, 3 }的类型auto lmd = [](auto param) {  };lmd({ 1, 2, 3 });  // error: 无法推导{ 1, 2, 3 }的类型
0 0
原创粉丝点击