【问题标题】:C++ template class inheritance and operators useC++模板类继承和运算符使用
【发布时间】:2011-11-09 02:14:01
【问题描述】:

我有一个定义运算符的模板类,它适用于模板参数。 我有另一个从这个类继承的类,我当然希望运算符被继承。

考虑一下:

template <typename T>
class A
{
public:
  A(const T& x) : x_(x) {}
  A operator-(const A& other) 
  { 
    A r(*this);
    r.x_ -= other.x_;
    return r;
  }

  T x() const { return x_; }

private:
  T x_;
};

template <typename T>
class B : public A<T>
{
  // additional stuff here
};

我似乎无法将 A 中声明的任何运算符用于 B 类型的对象。

例子:

int main()
{
  // Fine
  A<int> a(5);
  A<int> b(2);
  A<int> c = a - b;
  std::cout << c.x() << std::endl;

  // Won't compile :( 
  B<int> d(5);
  B<int> e(2);
  B<int> f = d - e;
  std::cout << f.x() << std::endl;

  return 0;
}

将触发以下错误:错误:请求从“A”转换为非标量类型“B”

有什么办法可以做到吗?我真的很想避免在 B 类中重写所有代码(这将是完全相同的)。

谢谢!

【问题讨论】:

    标签: c++ templates operators


    【解决方案1】:

    问题不在于调用操作符,而是从A的返回值构造B

    如果B 不包含除其基类A 之外的任何数据,您可以从AB 提供构造函数:

    template <typename T>
    class B : public A<T>
    {
    public:
         B(const T& x) : A<T>(x) {}
         B(const A<T>&x) : A<T>(x) {}
      // additional stuff here
    };
    

    如果B 确实包含自己的数据,那么您肯定需要实现operator- 来处理这些数据字段吗?

    【讨论】:

    • 在我的例子中,它是一个 Point 类,因此 A 类具有 x,y 坐标,B 类包含标志 (uint32)。我认为您的解决方案可以在这里工作。我无法编译你的解决方案。
    • @zedxz。道歉。现在指的是A&lt;T&gt;&amp;,而不是A;可能是编译问题。
    【解决方案2】:

    当我尝试这个时,Visual Studio 给了我错误cannot convert from 'A&lt;T&gt;' to 'B&lt;T&gt;'

    所以我尝试将变量 f 的类型从 B&lt;int&gt; 更改为 A&lt;int&gt; 并正确编译。这是我所拥有的:

    int main()
    {
      // Fine
      A<int> a(5);
      A<int> b(2);
      A<int> c = a - b;
      std::cout << c.x() << std::endl;
    
      // does compile :)
      B<int> d(5);
      B<int> e(2);
      A<int> f = d - e;
      std::cout << f.x() << std::endl;
    
      return 0;
    }
    

    但是,我认为这不是您想要的,因为如果您找到一种将 f 从 B 转换为 A 的方法,您会发现所有特定于 B 的数据成员都已被删除。如果您考虑处理器在幕后所做的事情,这是有道理的。当它看到operator- 的返回类型是A 时,它正好返回sizeof(A) 字节的数据。除此之外的任何额外数据(例如与 B 关联的数据)都将被删除。因此,为了安全起见,编译器会告诉您,如果您尝试将返回值放入 B 类型的变量中,那么您就不走运了。

    【讨论】:

      猜你喜欢
      • 2020-03-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-12-05
      • 2021-04-24
      相关资源
      最近更新 更多