C++的完美轉(zhuǎn)發(fā)(Perfect Forwarding)是C++11引入的一個(gè)新特性,它允許函數(shù)模板將參數(shù)以原始形式(保持參數(shù)的類型和值類別)傳遞給其他函數(shù)。這意味著傳遞給完美轉(zhuǎn)發(fā)的函數(shù)的參數(shù)可以是左值或右值、const或非const、引用或非引用等。
為了實(shí)現(xiàn)完美轉(zhuǎn)發(fā),C++引入了兩個(gè)新的概念:通用引用(Universal Reference)和std::forward函數(shù)模板。
通用引用(Universal Reference):通用引用是一種特殊類型的引用,它可以同時(shí)綁定到左值和右值。通用引用的定義是在模板參數(shù)列表中使用T&&,其中T是一個(gè)模板參數(shù)。當(dāng)T是一個(gè)左值時(shí),T&&表示一個(gè)左值引用;當(dāng)T是一個(gè)右值時(shí),T&&表示一個(gè)右值引用。通用引用通常用于實(shí)現(xiàn)完美轉(zhuǎn)發(fā)。
std::forward函數(shù)模板:std::forward函數(shù)模板用于將參數(shù)完美轉(zhuǎn)發(fā)給另一個(gè)函數(shù)。它的基本語法如下:
template<typename T>
constexpr T&& forward(typename std::remove_reference<T>::type& arg) noexcept;
std::forward函數(shù)模板接受一個(gè)通用引用參數(shù)arg,并使用std::remove_reference從中提取原始類型。然后,它根據(jù)arg的類型(左值或右值)返回相應(yīng)的引用。這樣,我們可以確保傳遞給目標(biāo)函數(shù)的參數(shù)保持其原始類型和值類別。
下面是一個(gè)簡單的完美轉(zhuǎn)發(fā)示例:
#include <iostream>
#include <utility>
void func1(int& x) {
std::cout << "func1(int&): "<< x << std::endl;
}
void func2(int&& x) {
std::cout << "func2(int&&): "<< x << std::endl;
}
template<typename T>
void wrapper(T&& arg) {
func1(arg);
func2(std::forward<T>(arg));
}
int main() {
int x = 42;
wrapper(x); // 輸出:func1(int&): 42 和 func2(int&&): 42
wrapper(42); // 輸出:func1(int&): 42 和 func2(int&&): 42
wrapper(std::move(x)); // 輸出:func1(int&): 42 和 func2(int&&): 42
}
在這個(gè)示例中,wrapper函數(shù)模板使用完美轉(zhuǎn)發(fā)將參數(shù)arg傳遞給func1和func2。注意,盡管arg在調(diào)用func1時(shí)是一個(gè)左值引用,但在調(diào)用func2時(shí)它是一個(gè)右值引用,這是因?yàn)閟td::forward會根據(jù)參數(shù)的原始類型返回相應(yīng)的引用。