【问题标题】:Getting around private copy constructor/copy assignment C++绕过私有复制构造函数/复制分配 C++
【发布时间】:2014-05-01 06:09:45
【问题描述】:

我有一个对象,它在初始化时传递了一个大型数据结构:

class foo {
public: 
   foo(const BigData& data);

   command();

}

BigData 的复制构造函数和复制赋值运算符是私有的,这是正确的。

但是,我需要更改class foo,以便command() 可以访问BigData。考虑到程序的结构,通过command(const BigData& data) 非常困难,所以我想做以下事情:

class foo {
public: 
   foo(const BigData& data);

   command();
private:
   BigData m_data;
}

但是如何在没有复制构造函数或复制赋值的情况下初始化m_data?我也不喜欢data 上的std::move 的想法,因为它需要在调用者的上下文中保持有效的对象。

注意:我已将成员声明为引用(即const BigData& m_data),但这不能在 icpc 下编译:

error: foo provides no initializer for reference member "m_data"

我用过foo(const BigData& data) : m_data(data) 和foo(const BigData& data) { m_data = data; }。

【问题讨论】:

  • 如果你不想复制,那么你可能需要存储一个引用(或一个指针,如果你想允许重新就位和持有 nullptr 的可能性。)跨度>
  • "如何在没有复制构造函数或复制赋值的情况下初始化 m_data?" - 你不能。正如所写的BigData 不可复制,除非BigData 的成员和朋友可以复制,我认为foo 不是其中之一(而且听起来你也不想要一份副本)。使用 const-reference 并确保传递的 BigData 至少与 foo 实例一样长。
  • "我已经将成员声明为引用..." 它必须是 const 引用,因为您正试图从传入的 const 引用初始化它。
  • 这是一个const 参考。
  • 你打错了一些东西。显示您的类现在的样子,直接从您实际尝试编译的代码中复制和粘贴。

标签: c++


【解决方案1】:

存储引用怎么样?

class foo
{
public: 
   foo(const BigData& data) : m_data(data) {}
   command();
private:
   const BigData & m_data;
};

【讨论】:

    【解决方案2】:

    如果BigData 没有复制构造函数和赋值运算符,作者不希望您复制它。但是,您可以自己对它进行 const 引用,如下所示:

    class foo {
    public: 
       foo(const BigData& data) : m_data(data) {}
       command();
    private:
       const BigData &m_data;
    };
    

    现在您的command() 成员函数可以访问已传递给foo 的构造函数的BigData。

    要记住的重要一点是BigData 对象的生命周期与foo 对象的生命周期无关。您需要确保当foo::command() 运行时,已传递给foo 的构造函数的BigData 在附近。否则,由于悬空引用,您的程序会出现未定义的行为。

    另一种选择是让您自己的班级类似于BigData,然后将他们班级的副本复制到您的班级中。不过,就编程工作而言,这可能令人望而却步。

    【讨论】:

      【解决方案3】:
      class foo {
      public: 
       foo(const BigData& data);
      
       command();
      private:
       const BigData& m_data;
      }
      
      // constructor
      foo::foo(const BigData& data)
      : m_data( data ) 
      {
       // usual stuff
      }
      

      【讨论】:

        猜你喜欢
        • 2011-09-12
        • 2016-07-17
        • 2013-12-19
        • 1970-01-01
        • 2011-01-26
        • 1970-01-01
        • 2011-01-28
        • 2016-10-13
        • 1970-01-01
        相关资源
        最近更新 更多