【问题标题】:Modify class member though operator override with scalar argument通过使用标量参数的运算符覆盖修改类成员
【发布时间】:2018-12-07 19:13:30
【问题描述】:

我正在编写一个具有std::vector 作为成员的类,我希望能够使用默认运算符+/+=*/*= 批量修改其数据等以标量为参数,例如

MyClass<float> obj;
obj += 4.0;

我正在尝试将运算符重载定义为:

template <class _type> 
matrix2D<_type>& matrix2D<_type>::operator=(matrix2D<_type> _mat){
    std::swap(_mat,*this);
    return *this;
};

template <class _type>
template <typename _input_type>
myClass<_type> myClass<_type>::operator*(_input_type _val) { 
    for (int i = 0; i < data.size(); ++i) data[i] *= _val; 
    return *this;
};

template <class _type>
template <typename _input_type>
myClass<_type> myClass<_type>::operator*=(_input_type _val) { 
    for (int i = 0; i < data.size(); ++i) data[i] *= _val; 
    return *this;
};

我没有收到编译或运行时错误,但值保持不变。我尝试了多种不同类型的返回值(MyClass&amp;void)并将myClass 对象作为参数传递。我错过了什么?

【问题讨论】:

  • 您似乎想要的已经以std::valarray 的形式存在。
  • 由于您的问题的可能原因,赋值运算符应该返回*this通过引用。而且您的operator* 也是错误的,它不应该修改this 或其成员。我建议你阅读例如this operator overloading reference,尤其是仔细看the canonical implementations。当然还有read a few good books
  • 据我所见,您的实例已被修改(即使是 operator* :-/ )。
  • 我遵循here 中的指导方针。我试过通过引用返回类对象——结果是一样的。我不明白为什么我不应该修改this
  • 如果您有a = b * c,是否应该修改bc?不,这不是乘法(其他其他算术运算)的工作原理。

标签: c++ templates operator-overloading


【解决方案1】:

不要天真地写这个;y,否则它将成为世界上最慢的实现。绝对不要使用std::val_array,因为它没有使用我知道的任何编译器进行优化。它的概念已经死在水中我的博士工作中有一个矩阵课程,如果你关心的话,可以在那里获得灵感:https://github.com/kvahed/codeare/blob/master/src/matrix/Matrix.hpp

根据经验,坚持使用std::vector 并使用&lt;algorithm&gt; 中的功能,例如std::accumulatestd::transform、...。始终实现运算符的赋值版本并在其他任何地方使用它。

例如,涵盖标量和矩阵元素乘法:

template <typename T>
class Matrix {
  public:
  ...
  Matrix<T>& operator*=(const T& t) {
    if (t != T(1)) {
      std::transform(
        v_.begin(), v_.end(), v_.begin(), std::bind2nd(std::multiplies<T>(), t));
    }
    return *this;
  }
  Matrix<T>& operator*=(const Matrix<T>& m) {
    std::transform(
      v_.begin(), v_.end(), m.begin(), v_.begin(), std::multiplies<T>()));
    return *this;
  }
  template<typename S>
  Matrix<T> operator* (const S& s) {
    return *this *= s;
  }
  ...
  private:
    std::vector<T> v_;
}

但这忽略了您的 CPU 能够执行的 SIMD 指令集: https://github.com/kvahed/codeare/blob/master/src/matrix/SIMDTraits.hpp

但有些事情您应该记住,但事实证明这些事情并非微不足道。特别是,当您的矩阵未在堆上分配时,内存可能是未对齐的。这将彻底杀死你。手动计算会更快。 https://github.com/kvahed/codeare/blob/master/src/matrix/Allocator.hpp

说真的,要正确构建您想要构建的东西需要大量的工作和测试代码。

TLDR:如果您正在寻找简单的实现,请使用 &lt;algorithm&gt; 远离 val_array。随意使用我的东西。如果您有任何问题,请随时。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-12-06
    • 1970-01-01
    • 2013-06-10
    • 1970-01-01
    • 1970-01-01
    • 2021-11-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多