C++11常用新特性——完美转发

完美转发

完美转发,旨在解决在函数模板中准确无误地转发参数的值,还能保证被转发参数的左、右值属性不变。

在早期的 C++ 中,当你通过一个函数向另一个函数传递参数时,参数的左值/右值属性会丢失,这意味着即使有可用的移动构造函数,编译器也只能调用拷贝构造函数。

为了解决这个问题,C++11 引入了新的工具和概念:右值引用和移动语义,所以,能否实现完美转发,决定了该参数在传递过程使用的是拷贝语义还是移动语义。

1)通用引用/转发引用: 在函数模板中,如果一个参数的类型为 T&&,并且这个类型 T 是通过模板推断得来的,那么这个参数就不是一个普通的右值引用,而是所谓的“通用引用”或“转发引用”。这种引用可以绑定到一个左值上(此时 T 被推断为 Type&),也可以绑定到一个右值上(此时 T 被推断为 Type)。

示例:

template<typename T>
void wrapper(T&& arg) {
    // some operations
}

2)forwardforward 是一个用于实现完美转发的模板函数,它可以保持一个值的左值/右值属性。如果传递给 forward 的参数是一个右值引用,它就会返回一个类似的右值引用,如果传递的是左值引用,它就返回一个左值引用。

示例:

template<typename T>
void wrapper(T&& arg) {
    // 使用 forward 转发 arg
    // 如果 arg 是右值,它被转发为右值;如果是左值,它被转发为左值
    some_function(forward<T>(arg));
}

在这个例子中,forward(arg) 保证 arg 作为与原始参数同样类型的引用(左值或右值)被转发给 some_function 函数。

下面是一个完整实例:

#include 
#include   // for forward

using namespace std;

// 普通函数,用以检验参数的左/右值性
void foo(int& x) { cout << "foo(int&): " << x << endl; }
void foo(int&& x) { cout << "foo(int&&): " << x << endl; }

// 完美转发模板函数
template <typename T>
void bar(T&& x) {
    foo(forward<T>(x));
}

int main() {
    int a = 5;

    // 使用左值调用 bar,bar 内部会调用 foo(int&)
    bar(a);

    // 使用右值调用 bar,bar 内部会调用 foo(int&&)
    bar(10);

    return 0;
}

你可能感兴趣的:(C++学习/笔记,c++,开发语言)