为用户定义的类型提供swap()的原因是什么? [英] What's a reason to provide a swap() for the user defined type?

查看:112
本文介绍了为用户定义的类型提供swap()的原因是什么?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

例如,我有一个管理POSIX fd的类:

For example, I have a class which manages a POSIX fd:

class remote_connection:
{
public:
  explicit remote_connection( int socket_fd ) : socket_fd(socket_fd) {}
  ~remote_connection() { close( socket_fd); }

  /* no copy semantic */
  remote_connection( const remote_connection& other ) = delete;
  remote_connection& operator=( const remote_connection& rhs ) = delete;

  remote_connection( remote_connection&& other )
  {
    socket_fd = other.socket_fd;
    other.socket_fd = -1;
  }

  remote_connection& operator=( remote_connection&& rhs )
  {
    close( socket_fd );
    socket_fd = rhs.socket_fd;

    rhs.socket_fd = -1;

    return *this;
  } 

private:
  int socket_fd;
};

在代码中的某处:

/* let '42' and '24' be a valid fds */
remote_connection cl_1( 42 ), cl_2( 24 );

...

using std::swap;

swap( cl_1, cl_2 );

对于 remote_connection ADL的这种实现找不到用户定义的 swap 并回退到std名称空间,其中<​​code> remote_connection 没有特殊化,因此编译器从 std :: swap< T>()模板实例化 std :: swap< remote_connection>()函数功能。该函数实现调用move ctor和move赋值运算符,从而导致对象交换其内容。

For such an implementation of a remote_connection ADL has found no user defined swap and fall-backs to the std namespace where there's no specialization for the remote_connection, so compiler instantiates a std::swap<remote_connection>() function from a std::swap<T>() template function. That function implementation invokes move ctor and move assignment operator which causes objects to exchange their content.

我可以实现 swap()表示 remote_connection 会导致相同的结果。

I could implement a swap() for the remote_connection that would result in the SAME result.

所以问题是我该怎么办在 swap 中特定于该类,以致模板std :: swap< T>()不能?还是为什么如果我们的类型可以由编译器实例化,甚至对于管理不重要的子对象(PO​​SIX fd,指针等)的类型,为什么还要为它提供一种实现呢?

So the question is what can I do so specific within swap for the class that a template std::swap<T>() can't? Or why we should provide an implementation for a type if it can be instantiated by a compiler even for types which manage not trivial sub-objects (POSIX fd, pointers,...)?

推荐答案

全局 std :: swap 需要创建一个临时文件。基于自定义类的交换将了解类的内部,并且可以更有效地执行交换,而不必创建该类类型的另一个变量。

The global std::swap requires creation of a temporary. A custom class based swap will be aware of the internals of the class, and can do the swap more efficiently, without having to create another variable of the class type.

In您的情况是,内部交换可以只交换内部 socket_id 的值,而不必在move构造函数和move赋值运算符中做所有额外的工作(将被调用两次)

In your case, that internal swap can just swap the internal socket_id values, without having to do all that extra stuff in the move constructor and move assignment operator (which will be called twice).

这篇关于为用户定义的类型提供swap()的原因是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆