C++11 新特性:自动类型推导 auto 和 decltype(中)

今天我们来聊聊 decltype 关键字,它是 C++11 新增的一个关键字,和 auto 的功能一样,都是用来在编译时期进行自动类型推导。

decltype 是「declare type」的缩写,译为「声明类型」。

既然已经有了 auto 关键字,为什么还需要 decltype?

因为 auto 并不适用于所有的自动类型推导场景,在某些特殊情况下 auto 用起来非常不方便,甚至压根无法使用,所以引入了 decltype 关键字。

下面通过介绍 decltype 的用法,体会一下和 auto 的不同。

decltype 的用法

decltype 关键字用于检查实体的声明类型或表达式的类型,并且不会对表达式进行求值。

1、基本用法

decltype 可以直接用于变量,获取其类型。

cpp 复制代码
int x = 1;
decltype(x) y = x; // y 的类型为 int
decltype(10.8) z = 5.5; //z 的类型为 double
decltype(z + 100) a;  //a 的类型为 double

2、与复杂表达式一起使用

decltype 可以用于更复杂的表达式中。

cpp 复制代码
std::vector<int> v;
decltype(v.begin()) it = v.begin(); // it的类型为std::vector<int>::iterator

3、用于函数返回类型推导

在 C++11 及以后的版本中,decltype 可用于精确推导函数返回类型,尤其是当返回类型依赖于函数参数时。

cpp 复制代码
template<typename A, typename B>
auto add(A a, B b) -> decltype(a + b) {
    return a + b;
}

在这个例子中,函数 add 的返回类型通过 decltype 自动推导,这样函数就能够处理不同类型的参数,并返回正确的类型。

4、结合autodecltype用于自动类型推导

decltype还可以与auto结合使用,以便在需要类型匹配的场景中自动推导变量类型。

cpp 复制代码
auto x = 1;
decltype(auto) y = x; // y的类型为int

decltype 推导规则

上面的例子让我们初步感受了 decltype 的用法,但你不要认为 decltype 就这么简单,它的用法实际上可以非常复杂。

如果 decltype(exp) 中的表达式 exp,其类型为 T,那么:

  • 如果 exp 的值类型是 xvalue(将亡值),decltype 推导出的类型是 T&&;

  • 如果 exp 的值类型是 lvalue(左值),decltype 推导出的类型是 T&;

  • 如果 exp 的值类型是 prvalue(纯右值),decltype 推导出的类型是 T。

上面这三条规则有点抽象,不像人说的话,其中的「值类型」,在后面的文章中会详细解释。

当前只要记住下面这三条规则,就能应对 90% 的场景:

  • 如果 exp 是一个不被括号()包围的表达式,或者是一个类成员访问表达式,或者是一个单独的变量,那么 decltype(exp) 的类型就和 exp 一致,这是最常见的情况。

  • 如果 exp 是函数调用,那么 decltype(exp) 的类型就和函数返回值的类型一致。

  • 如果 exp 是一个左值,或者被括号()包围,那么 decltype(exp) 的类型就是 exp 的引用;假设 exp 的类型为 T,那么 decltype(exp) 的类型就是 T&

代码示例

我们通过一个具体的例子来展示 decltype 的实际应用。

假设我们需要实现一个泛型函数,该函数能够根据传入参数的类型动态决定返回值的类型。

cpp 复制代码
#include <iostream>
#include <vector>

template<typename T>
auto multiply(T x, T y) -> decltype(x * y) {
    return x * y;
}

int main() {
    auto result1 = multiply(5, 4); // result1的类型为int
    std::cout << "int result: " << result1 << std::endl;

    auto result2 = multiply(3.14, 2.71); // result2的类型为double
    std::cout << "double result: " << result2 << std::endl;
}

在这个例子中,函数 multiply 能够根据传入参数的类型(无论是整型还是浮点型),通过 decltype 自动推导出正确的返回类型。这种类型推导不仅使代码更加灵活和通用,也保持了类型安全,避免了类型不匹配的错误。

decltype 提供了一种方式,来捕获表达式的类型,而不实际计算表达式的值。这在模板编程、泛型编程以及需要精确控制类型的场景中非常有用。结合 auto 关键字,decltype 为C++程序提供了更大的灵活性和表达能力。

相关推荐
2301_803554523 小时前
c++中类的前置声明
java·开发语言·c++
LyaJpunov9 天前
深入理解 C++ volatile 与 atomic:五大用法解析 + 六大高频考点
c++·面试·volatile·atomic
小灰灰搞电子9 天前
Qt PyQt与PySide技术-C++库的Python绑定
c++·qt·pyqt
时空自由民.9 天前
C++ 不同线程之间传值
开发语言·c++·算法
Ray_19979 天前
C++二级指针的用法指向指针的指针(多级间接寻址)
开发语言·jvm·c++
双叶8369 天前
(C语言)Map数组的实现(数据结构)(链表)(指针)
c语言·数据结构·c++·算法·链表·哈希算法
Jay_5159 天前
C++ STL 模板详解:由浅入深掌握标准模板库
c++·学习·stl
Cyrus_柯9 天前
C++(面向对象编程——继承)
开发语言·c++·算法·面向对象
Echo``10 天前
12.OpenCV—基础入门
开发语言·c++·人工智能·qt·opencv·计算机视觉
十秒耿直拆包选手10 天前
C++:动态库相关文件
c++