1

In the following code example, because I compare two std::map objects, I am compelled to implement MyId::operator==().

MyId is a simple class: basically a wrapper over an array. This made me wonder why an equality operator is mandated: why aren't we given a default bitwise comparator? After all, we are given a default assignment operator, which does a bitwise memberwise copy between objects.

I understand the difference between deep and shallow copies and the need for assignment and equality operators. My question is why is there not a default "bitwise equality check" when there is a default assignment?

#include <iostream>
#include <map>
#include <cstring>

typedef int myid[ 3 ];

struct MyId
{
  myid id_;
  bool operator<( const struct MyId& other ) const { return this < &other; }
  bool operator==( const struct MyId& other ) const
  {
    return ( 0 == std::memcmp( id_, other.id_, sizeof( myid ) ));
  }
};

int main( int argc, char* argv[] )
{
  std::map< MyId, int> map;
  MyId id = { 1, 2, 3 };
  map[ id ] = 5;

  std::map< MyId, int> map2;
  map2[ id ] = 5;

  // This forces implementation of MyId::operator==():
  std::cout << std::boolalpha <<( map == map2 ) << std::endl;

  MyId i1 = { 4, 5, 6 };
  MyId i2 = { 7, 8, 9 };

  // No required implementation of MyId::operator=():
  i1 = i2;

  return 0;
}

Update: Publicly corrected my brain-fart RE: bitwise vs. memberwise default assignment operator.

4

1 回答 1

3

After all, we are given a default assignment operator, which does a bitwise copy between objects.

No it doesn't. On the contrary, the default copy-assignment operator is constructed in such way it copy-assigns each and every member of the object. Depending on how copy-assignment operators are implemented in the field types, the result might be far from just a bitwise copy.

Anyway, the default copy-assignment (or copy-construction, or move-assignment, or even destruction) behavior is designed in a way to fit common basic needs. Based on the language specification, it's available most of the times, but there are known situations when the language is uncertain about your semantics, and it requires explicit definitions for these.

The equality operator is different. The actual equality relation is not implied by the language syntax, but purely by the semantics. Compiler don't know how you see two instances of a class 'equal' - therefore it demands you to tell him.

于 2017-05-26T01:20:03.477 回答