是否可以在他自己的方法中将一个对象取消引用到另一个对象?

Posted

技术标签:

【中文标题】是否可以在他自己的方法中将一个对象取消引用到另一个对象?【英文标题】:Is it possible to dereference an object to another object inside his own method? 【发布时间】:2020-02-19 14:32:48 【问题描述】:

我有一个关于 C++ 问题的问题。假设我有一个非常大的班级,叫做BigClass,我说BigClass* foo = new BigClass();

假设我在 BigClass 中有一个方法,它定义了另一个 BigClass 类型的本地对象 tmp,在方法结束时,我通过使用 tmp 做一些事情来检查是否有错误,如果没有,我想要将this 取消引用到该对象。我不想将所有参数从tmp 复制到this,因为对象太大,过程会很慢。有没有办法在自己的方法中取消引用对象?

例子:

class BigClass

    int a;
    long b;
    std::vector<int> c;
    // other members...

    void replace()
    
        BigClass* tmp = new BigClass();
        // do some calculations with tmp
        *this = tmp; // problem
    

为什么 *this = tmp 是个问题?

我定义了一个 operator= 来做这样的事情:

this.a = src.a;
this.b = src.b;
this.c = src.c;
.
.
.

但是我复制了所有成员变量,这很慢。我想简单地取消引用对象而不是复制所有成员变量。

【问题讨论】:

请提供minimal reproducible example 如果你不想复制,move它。虽然像this = new Bigclass() 这样的东西是非法的。 "有什么方法可以在对象自己的方法中取消引用?"不太清楚,你是在问你是否可以做*this?是的你可以。一些代码真的很有帮助 如果你添加一个你正在尝试做的例子,我会投票支持重新开放 我不想将所有参数从 tmp 复制到 this — 我假设您的意思是复制所有成员变量/子对象。那么为什么?你不抄袭的理由是什么?如果出于性能原因,您可以简单地移动它们,*this = std::move(tmp); 【参考方案1】:

如果你不想复制,你可以移动它来代替:

struct BigClass 
    void func() 
        BigClass tmp;

        *this = std::move(tmp);
    
;

移动操作通常不涉及动态分配或大缓冲区的复制。

如果您关注rule of zero,将为您定义移动赋值运算符。

否则,您始终可以使用默认运算符来定义它:

struct BigClass 
    BigClass& operator=(BigClass&&) = default;

    // ...
;

您也可以编写自己的运算符,但默认的运算符通常可以很好地完成这项工作。

struct BigClass 
    //          quite important ----v------v
    BigClass& operator=(BigClass&& rhs) noexcept 
        this->a = std::move(rhs.a);
        this->b = std::move(rhs.b);
        this->c = std::move(rhs.c);
    

    // ...
;

移动操作通常非常快,比new 快得多。


或者,您也可以新建一个对象并为其分配指针:

struct BigClass 
    auto replace() -> BigClass* 
        auto tmp = new BigClass;

        // ...

        return tmp;
    
;

请注意,因为它涉及动态分配,因此速度要慢得多。

【讨论】:

非常感谢这是一个非常有帮助的答案:) @Delprof 除非必要,否则我会避免使用共享指针。最好是唯一的指针。 我的问题是我使用的是 C++10 并且 move() 无法编译:D 所以我搜索了一些使用共享指针的解决方案 @Delprof 当然你可以转换为右值引用。 std::move 只是对右值的强制转换,没有别的。编写 move 实现并不那么具有挑战性。

以上是关于是否可以在他自己的方法中将一个对象取消引用到另一个对象?的主要内容,如果未能解决你的问题,请参考以下文章

在javascript中将对象数组复制到另一个数组而没有对象引用(深拷贝)

在Django中将模型对象从模型复制到另一个模型

我可以以任何方式从 OpenCV 对象取消引用中将数据分配给双重函数返回检索吗?

在javascript中将对象数组复制到另一个数组中(深度复制)

XMM 寄存器中的取消引用指针(收集)

如何在sequelize中将外键引用到另一个外键?