我正在编写一个模板化类,该类负责将某些数据复制到本地函数中以及从本地函数中复制数据。我构想了两种不同的机制来执行此操作。通过子类或通过引用。哪个更有意义,是“正确”的方法呢?

namespace subclass {
struct array {
  int a, b, c, d;
};

template <typename T> class inout : public T {
private:
  static_assert(std::is_pod<T>::value);

  T *p;

public:
  inout(T *_p) : p(_p) { memcpy(this, p, sizeof(T)); }
  ~inout(void) { memcpy(p, this, sizeof(T)); }
};

void subr(array *args, int) {
  inout<array> local(args);

  local.a = local.b + local.c + local.d;
}
}

namespace reference {
struct array {
  int a, b, c, d;
};

template <typename T> class inout {
private:
  static_assert(std::is_pod<T>::value);

  T *p;
  T &l;

public:
  inout(T &_l, T *_p) : p(_p), l(_l) { memcpy(&l, p, sizeof(T)); }
  ~inout(void) { memcpy(p, &l, sizeof(T)); }
};

void subr(array *args, int) {
  array local;
  inout<array> raii(local, args);

  local.a = local.b + local.c + local.d;
}
}

最佳答案

在我看来,您的解决方案似乎是他们尝试以困难的方式做一件简单的事情。
如果要复制,为什么不简单复制?

void subr(array *args, int) {
  array local = *args;

  local.a = local.b + local.c + local.d;

  *args = local;
}


如果您希望在范围的末尾自动复制,那么您会更简单:

template <typename T>
class AutoCopy {
private:
   T   m_copy;
   T * m_original;

public:
   AutoCopy(T * original) : m_copy(*original), m_original(original) {}
   ~AutoCopy() { *m_original = m_copy; }

   T & get() { return m_copy; }
};

void subr(array *args, int) {
  AutoCopy<array> c(args);
  c.get().a = c.get().b + c.get().c + c.get().d;
}


它适合你吗?这样,即使类型不是POD,它也能正常工作,如果它是常规的默认副本构造函数,则它将与memcpy()相同(如您在“常规副本构造函数”部分所见,here一样)。

即使您喜欢保留memcpy(),我认为拥有一个成员变量并将其复制到该变量中比从您的类型继承更清晰。

10-05 21:56