C++11 使用右值的最佳实践

标签 c++ c++11 reference

我是 C++11 的新手。事实上,直到最近,我都只使用动态分配进行编程,其方式类似于 Java,例如

void some_function(A *a){
   a->changeInternalState();
}

A *a = new A();
some_function(a);
delete a;

// example 2
some_function( new A() ); // suppose there is **no** memory leak.

现在我想用 C++11 重现类似的代码,但没有指针。

我需要能够将新创建的类 class A 直接传递给函数 useA()。如果我想用非 const 普通引用这样做似乎有问题,如果我用右值引用来做它会起作用。

代码如下:

#include <stdio.h>

class A{
public:
        void print(){
                ++p; // e.g. change internal state
                printf("%d\n", p);
        }

        int p;
};

// normal reference
void useA(A & x){
        x.print();
}

// rvalue reference
void useA(A && x){
        useA(x);
}

int main(int argc, char** argv)
{
        useA( A{45} );   // <--- newly created class 

        A b{20};

        useA(b);

        return 0;
}

它可以正确编译和执行,但我不确定这是否是完成工作的正确可接受方式?

是否有针对此类操作的一些最佳实践?

最佳答案

通常您不会设计代码以修改临时对象。然后你会把你的打印函数写成:

void useA(A const & x){
    x.print();
}

并将A::print 声明为const。这绑定(bind)到右值和左值。您可以将 mutable 用于类成员变量,这些变量可能会更改值但对象不会逻辑上更改状态。

另一个计划是只保留A &,但是写:

{ A temp{45}; useA(temp); }

如果您真的想修改一个临时对象,您可以像您在问题中所做的那样编写一对左值和右值重载。我相信对于这种情况,这是可以接受的做法。

关于C++11 使用右值的最佳实践,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31148999/

相关文章:

rust - 如何在Rust中将ref转换为en16的枚举值(基本枚举类型)?

c++ - Placement-new 是否引入了序列点?

c++ - ODR 使用的空类的优化

c++ - 按值捕获 shared_ptr 的 lambda 如何影响它的 use_count()?

c++ - 如何使用 dynamic_cast 运算符识别失败的强制转换?

c# - 试图理解这个 : bool variables are value types in C#

c++ - 如何在 Eigen 中近似比较 vector ?

c++ - 导航到 Visual Studio 中重写的函数

c++ - USB检测使用qt应用程序

C++11 - 检测运算符 new[] 的方法