Please consider the following snippet:
class Pin
{
public:
Pin()
{
}
};
class Connection
{
Pin& _from;
Pin& _to;
public:
Connection(Pin& from, Pin& to)
: _from(from), _to(to)
{
}
};
class Device
{
Pin _a, _b;
Connection _int_conn;
public:
Device()
: _int_conn(_a, _b)
{
}
};
Now I’d like to define operator= so that Device can be copied one to another:
int main()
{
Device a, b;
a = b;
}
Of course, the default operator= doesn’t suffice because the Connection class holds two references. For this particular operation, it is however desirable that the Device copies all other properties and leaves the references intact (since they are expected to always point to the ‘parent’ pins).
On the other hand, the Connection class can be also used by user, and then the two pins can belong to any other class. In this case, although copying other properties may be beneficial, it seems a bit incorrect to use operator= for that. In other words:
int main()
{
Pin a, b, c, d;
Connection y(a, b), z(c, d);
y = z;
}
to copy non-reference members seems wrong to me.
Moreover, if I ever decided to change references to pointers, I’d probably want operator= to copy them as well.
Am I right here? What is the best course of action? I think about defining an additional method like:
void Connection::copy_properties(Connection& rhs)
or just copying them in Device::operator=.
Is this an invariant of
Connectionor ofDevice? If the latter, consider this version ofConnection:That is to say, this version has somewhat more obvious copy semantics. Then
Device::operator=now has to make sure to not break theDeviceinvariant (e.g. assign whatever needs assigning while leaving_int_connunchanged). And in fact making_int_connaconstmember can enforce that; but that’s only as useful as theconstinterface ofConnection.