c++ decltype關(guān)鍵字的用法
1. decltype關(guān)鍵字的用途是什么
給定變量的名稱或者表達(dá)式,decltype返回變量或者表達(dá)式的類型。如下所示:
const int i = 0; // decltype(i) is const int
bool f(const Widget& w); // decltype(w) is const Widget&,decltype(f) is bool(const Widget&)
struct Point {
int x, y; // decltype(Point::x) is int, decltype(Point::y) is int
};
Widget w; // decltype(w) is Widget
if (f(w)) ... // decltype(f(w)) is bool
template<typename T>class vector {
public:
...
T& operator[](std::size_t index);...
};
vector<int> v; // decltype(v) is vector<int>
if (v[0] == 0) ... // decltype(v[0]) is int&
2.decltype主要應(yīng)用場(chǎng)景是模板函數(shù)
decltype在實(shí)際的開發(fā)中主要用于模板函數(shù)中,函數(shù)的返回值依賴于模板參數(shù)類型的情況。如下authAndAccess函數(shù)的返回值類型依賴于Container的元素類型。
template<typename Container, typename Index>
auto authAndAccess(Container& c, Index i) -> decltype(c[i]) {
authenticateUser();
return c[i];
}
此處的返回值auto并非類型推導(dǎo)的意思,而是C++ 11中的函數(shù)返回類型后置的表達(dá)方式,表明函數(shù)的返回類型在參數(shù)列表之后。函數(shù)返回類型后置的優(yōu)勢(shì)在于我們可以用函數(shù)的參數(shù)來(lái)指定返回值。
在c++ 14中auto關(guān)鍵字可以獨(dú)立用于對(duì)函數(shù)的返回值進(jìn)行類型推導(dǎo),而不必采用c++ 11中的返回返回類型后置的聲明方式:
template<typename Container, typename Index>
auto authAndAccess(Container& c, Index i) {
authenticateUser();
return c[i]; // return type deduced from c[i]
}
但上述寫法在實(shí)際應(yīng)用針對(duì)具體case可能存在問(wèn)題,比如如果operator[]返回T&,auto的推導(dǎo)機(jī)制會(huì)返回T,下面的就會(huì)編譯失敗:
std::deque<int> d; ... authAndAccess(d, 5) = 10; //return d[5], then assign 10 to it; this won't compile!
因?yàn)楦鶕?jù)auto的推導(dǎo)機(jī)制,authAndAccess返回的是右值,所以編譯不通過(guò)。authAndAccess函數(shù)需要聲明為如下方式才可以保證該示例編譯通過(guò)。
template<typename Container, typename Index>
decltype(auto) authAndAccess(Container& c, Index i){
authenticateUser();
return c[i];
}
decltype(auto)不僅僅可以用于函數(shù),也可以用于變量,可以完美推導(dǎo)變量的類型。
Widget w; const Widget& cw = w; auto myWidget1 = cw; // auto type deduction: myWidget1's type is Widget decltype(auto) myWidget2 = cw; // decltype type deduction: myWidget2's type is const Widget&
再回到authAndAccess函數(shù)
template<typename Container, typename Index> decltype(auto) authAndAccess(Container& c, Index i);
注意到Container是一個(gè)非const的左值引用,這意味著用戶可以修改Container內(nèi)元素的值,同時(shí)也意味不能傳遞右值引用給它。
另外右值容器一般是一個(gè)臨時(shí)對(duì)象,會(huì)在函數(shù)調(diào)用結(jié)束后不久被銷毀,所以當(dāng)用戶傳入一個(gè)右值引用的時(shí)候,一般我們要把返回元素拷貝它的一個(gè)副本。如何能夠在不重載authAndAccess函數(shù)的情況下使它同時(shí)支持左值和右值呢?答案是通用引用。
template<typename Container, typename Index> decltype(auto) authAndAccess(Container&& c,Index i);
為了保證推導(dǎo)結(jié)果的正確性,需要在實(shí)現(xiàn)中增加完美轉(zhuǎn)發(fā)(std::forward)功能。
template<typename Container, typename Index>
decltype(auto)authAndAccess(Container&& c, Index i){
authenticateUser();
return std::forward<Container>(c)[i];
} // c++ 14版本
template<typename Container, typename Index>
auto authAndAccess(Container&& c, Index i)
-> decltype(std::forward<Container>(c)[i])
{
authenticateUser();
return std::forward<Container>(c)[i];
} // c++ 11版本
3. decltype使用的極端case
decltype(auto) f1() { // decltype(x) is int, so f1 returns int
int x = 0;
...
return x;
}
decltype(auto) f2() { // decltype((x)) is int&, so f2 returns int&
int x = 0;
...
return (x);
}
返回了一個(gè)局部變量的引用。
4. 需要記住的:
1) decltype總是返回與變量或者表達(dá)式完全相同的類型;
2) 對(duì)于類型T的非名稱的左值表達(dá)式,decltype總是返回T&;
以上就是c++ decltype關(guān)鍵字的用法的詳細(xì)內(nèi)容,更多關(guān)于c++ decltype關(guān)鍵字的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
C++實(shí)現(xiàn)圖書管理系統(tǒng)源碼
這篇文章主要為大家詳細(xì)介紹了C++實(shí)現(xiàn)圖書管理系統(tǒng)源碼,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2022-03-03
C++第11版本中的一些強(qiáng)大的新特性小結(jié)
這篇文章主要介紹了C++第11版本中的一些強(qiáng)大的新特性小結(jié),需要的朋友可以參考下2015-12-12
C實(shí)現(xiàn)與 uint64_t 相同功能的類
本文給大家分享的是筆者實(shí)現(xiàn)的仿uint64_t的類,可以用在不支持uint64_t的平臺(tái)上,雖然現(xiàn)在功能還不完善,但是還是分享給大家,也算是給大家一個(gè)思路吧。2015-12-12
websocket++簡(jiǎn)單使用及實(shí)例分析
下面小編就為大家?guī)?lái)一篇websocket++簡(jiǎn)單使用及實(shí)例分析。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2016-05-05
c++ 類函數(shù)作為模板參數(shù)實(shí)現(xiàn)方式詳解
這篇文章主要介紹了c++ 類函數(shù)作為模板參數(shù)實(shí)現(xiàn)方式,在實(shí)現(xiàn)中加入增強(qiáng)邏輯,這種方式對(duì)代碼侵入性過(guò)高,而且無(wú)法控制該邏輯是否需要,如果不需要的話又得重新修改代碼實(shí)現(xiàn),需要的朋友可以參考下2023-03-03
C++ vector擴(kuò)容解析noexcept應(yīng)用場(chǎng)景
這篇文章主要介紹了C++ vector擴(kuò)容解析noexcept應(yīng)用場(chǎng)景,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-09-09
C語(yǔ)言實(shí)現(xiàn)學(xué)生選課系統(tǒng)完整版
這篇文章主要為大家詳細(xì)介紹了C語(yǔ)言實(shí)現(xiàn)學(xué)生選課系統(tǒng)的完整版,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2019-02-02
基于OpenCV和C++ 實(shí)現(xiàn)圖片旋轉(zhuǎn)
這篇文章主要介紹了基于OpenCV和C++ 實(shí)現(xiàn)圖片旋轉(zhuǎn),幫助大家更好的利用c++處理圖片,感興趣的朋友可以了解下2020-12-12

