1.語法
decltype
( 實體 ) (1) (C++11 起)
decltype
( 表達式 ) (2) (C++11 起)
解釋:
1) 如果實參是沒有括號的標識表達式或沒有括號的類成員訪問表達式,那么 decltype
產生以該表達式命名的實體的類型。如果沒有這種實體或該實參指名了一組重載函數(shù),那么程序非良構。
-
如果實參是指名某個結構化綁定的沒有括號的標識表達式,那么
decltype
產生其被引用類型(在關于結構化綁定聲明的說明中有所描述)。 -
如果實參是指名某個非類型模板形參的沒有括號的標識表達式,那么
decltype
生成該模板形參的類型(當該模板形參以占位符類型聲明時,類型會先進行任何所需的類型推導)。
2) 如果實參是其他類型為 T 的任何表達式,且
-
如果 表達式 的值類別是亡值,將會
decltype
產生 T&&; -
如果 表達式 的值類別是左值,將會
decltype
產生 T&; -
如果 表達式 的值類別是純右值,將會
decltype
產生 T。
如果 表達式 是返回類類型純右值的函數(shù)調用,或是右操作數(shù)為這種函數(shù)調用的逗號表達式,那么不會對該純右值引入臨時量。
如果 表達式 是除了(可帶括號的)立即調用以外的 (C++20 起)純右值,那么不會從該純右值實質化臨時對象:即這種純右值沒有結果對象。
該類型不需要是完整類型或擁有可用的析構函數(shù),而且類型可以是抽象的。此規(guī)則不適用于其子表達式:decltype(f(g())) 中,g() 必須有完整類型,但 f() 不必。
注意:
- 如果對象的名字帶有括號,那么它會被當做通常的左值表達式,從而 decltype(x) 和 decltype((x)) 通常是不同的類型。
- 在難以或不可能以標準寫法進行聲明的類型時,decltype 很有用,例如 lambda 相關類型或依賴于模板形參的類型。
2.關鍵詞decltype
示例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
|
#include <iostream> #include <type_traits> struct A { double x; }; const A* a; decltype(a->x) y; // y 的類型是 double(其聲明類型) decltype((a->x)) z = y; // z 的類型是 const double&(左值表達式) template < typename T, typename U> auto add(T t, U u) -> decltype(t + u) // 返回類型依賴于模板形參 { // C++14 開始可以推導返回類型 return t+u; } int main() { int i = 33; decltype(i) j = i * 2; std::cout << "i = " << i << ", " << "j = " << j << '\n' ; std::cout << "i 和 j 的類型相同嗎?" << (std::is_same_v<decltype(i), decltype(j)> ? "相同" : "不同" ) << '\n' ; auto f = []( int a, int b) -> int { return a * b; }; decltype(f) g = f; // lambda 的類型是獨有且無名的 i = f(2, 2); j = g(3, 3); std::cout << "i = " << i << ", " << "j = " << j << '\n' ; } |
輸出:
i 和 j 的類型相同嗎?相同
i = 33, j = 66
i = 4, j = 9
到此這篇關于C++ decltype
說明符的文章就介紹到這了,更多相關decltype 說明符內容請搜索服務器之家以前的文章或繼續(xù)瀏覽下面的相關文章希望大家以后多多支持服務器之家!
原文鏈接:https://zh.cppreference.com/w/cpp/language/decltype