代码之家  ›  专栏  ›  技术社区  ›  Steve

具有继承和虚拟基类的赋值运算符

  •  1
  • Steve  · 技术社区  · 15 年前

    我有一个抽象的虚拟基类foo,我从中派生出许多其他的类,它们的区别很小。我有一个创建派生类并返回foo*的工厂。我的一个更大的问题是我的运算符重载,我需要确保dfoo1不会操作dfoo(未显示)。我目前已经通过检查演员表是否失败来处理这个问题,但是我对这种方法很不满意。我必须使用基本实现,因为我只能从工厂返回基本类。如果这是最好的方法,没关系,我只是想确保这是有意义的,并且没有我遗漏的模式。关于如何处理这类事情的任何建议都非常感谢。

     class Foo
     {
        public:
              Foo(int x){...};
              Bar m_bar;
              virtual Foo& operator=(const Foo& f)
              {
                 m_bar = f.m_bar
              }
     }
    

    现在,我的派生类

    class DFoo : public Foo
    {
         DFoo(int x, int y):Foo(int x) {...}
         FooBar m_foobar;
    
         Foo& operator=(const Foo& rhs)
         {
            if(this != &rhs)
            {
    
                  Foo::operator=(rhs);
                  DFoo temp = static_cast<DFoo>(rhs);
    
                  if(temp != NULL)
                  {
                    m_foobar = static_cast<DFoo>(rhs).m_foobar;
                  }
                  else
                     throw exception(ex);
            }
         }
    }
    
    3 回复  |  直到 15 年前
        1
  •  1
  •   Nikolai Fetissov    15 年前

    你可能在找 boost::noncopyable .

        2
  •  1
  •   Beanz    15 年前

    在这种情况下,最明智的做法是声明赋值运算符并复制构造函数,但不定义它们。然后,如果代码中的某个地方有人试图复制,它将生成一个链接器错误。这本质上就是boost::nocopyable所具有的效果,只是您没有为这样一个简单而琐碎的任务引入外部库。

    编辑: 另外,如果将构造函数和运算符设为私有,则会得到一个编译器错误。

        3
  •  1
  •   Loki Astari    15 年前

    你不应该这样做:

     class DFoo
     {
         Foo& operator=(const Foo& rhs) ;
     };
    

    除非您明确希望支持将基类赋给派生类型(不太可能)。
    assignemtn运算符应如下所示:

     class DFoo
     {
         DFoo& operator=(DFoo const& rhs);  // You can only assign DFoo to a DFoo.
                                            // Now there is no way for DFoo1 to get assigned to a DFoo
     };
    

    在这个小例子中,您发布了编译器生成的默认赋值操作符,它应该可以按预期工作。你写作业员有什么特别的原因吗?