使用模板定义不同类型之间的操作

时间:2014-04-26 03:45:33

标签: c++ class templates operator-overloading

我创建了一个类模板(称为ThreeVector)并添加了允许不同类型之间的添加操作的功能。这是我头文件的相关部分:

template <class T>
class ThreeVector {
    private:
        T mx;
        T my;
        T mz;
        public:
        ThreeVector<T>(T, T, T);
            template <class X> 
        ThreeVector<T> operator+(const ThreeVector<X>&);
}

template <class T> 
ThreeVector<T>::ThreeVector(T x, T y, T z) { //initialize vector
    mx = x;
    my = y;
    mz = z;
}

template<class T> template<class X>
ThreeVector<T> ThreeVector<T>::operator+(const ThreeVector<X>& a) {
    ThreeVector<T> v(mx+a.mx, my+a.my, mz+a.mz);
    return v;
}

然后我称之为:

ThreeVector<double> a(1,2,3);
ThreeVector<float> b(4,5,6);
ThreeVector<double> c=a+b;

这给了我错误:

ThreeVector.h: In member function 'ThreeVector<T> ThreeVector<T>::operator+(const ThreeVector<X>&) [with X = float, T = double]':
ThreeVectorTest.cxx:33:   instantiated from here
ThreeVector.h:8: error: 'float ThreeVector<float>::mx' is private
ThreeVector.h:122: error: within this context
ThreeVector.h:9: error: 'float ThreeVector<float>::my' is private
ThreeVector.h:123: error: within this context
ThreeVector.h:10: error: 'float ThreeVector<float>::mz' is private
ThreeVector.h:124: error: within this context
make: *** [ThreeVectorTest] Error 1

如果a和b都是<double>,它就可以正常工作。知道为什么会这样吗?

1 个答案:

答案 0 :(得分:1)

类模板的访问权限可能有点令人困惑。

假设您有一个简单的类模板。

template <typename T>
class A
{
   public:
      A() {}

   private:
      T data;
};

使用

创建A的实例时
A<int> a1;
A<float> a2;

您正在使用模板定义两个类。好像你有两个班级一样:

class AInt
{
   public:
     AInt() {}
   private:
     int data;
};

class AFloat
{
   public:
     AFloat() {}
   private:
     float data;
};

很容易看出AInt无法访问AFloat的私有部分,反之亦然。

A<int>A<float>也是如此。

为了使operator+功能正常工作,您有两种选择:

  1. 将类模板的成员公开。
  2. 有一个朋友声明:

    template <class T>
    class ThreeVector {
       private:
          T mx;
          T my;
          T mz;
       public:
          ThreeVector<T>(T, T, T);
    
          template <class X> 
             ThreeVector<T> operator+(const ThreeVector<X>&);
    
          template <class X> friend class ThreeVector;
    };