Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Is it allowed to assign from an object that has some indeterminate values?

Consider the following class, which can either be in a "non-empty" or "empty" state, and in the "empty" state the other member is default initialized (hence has an indeterminate value):

struct MaybeInt {
  bool has_value;
  int value;

  MaybeInt()      : has_value(false) {}
  MaybeInt(int v) : has_value(true ), value(v) {}
};

Is it allowed to assign from a default-constructed MaybeInt, as in:

MaybeInt empty, another;
another = empty; // OK?

How about construction?

MaybeInt empty, another(empty); // OK?

Does the answer change if MaybeInt::value has type char?

like image 337
BeeOnRope Avatar asked Jan 24 '26 10:01

BeeOnRope


1 Answers

another = empty is indeed UB because empty.value has an indeterminate value and because the implicitly defined copy constructor of a class copies all members.

The trick is to place the member value in a union. This way the implicitly defined copy constructor of the union copies the object representation :

struct MaybeInt {
  bool has_value;
  union {
    int value;
    char _dumb;
    };

  MaybeInt()      : has_value(false) {}
  MaybeInt(int v) : has_value(true ), value(v) {}
  };

NB: This is a low level trick to have an optional that is trivially copyable. This is realy important for code execution speed. This class can be passed through function call on a cpu register, while it would be impossible if it were not trivially copyable.

like image 174
Oliv Avatar answered Jan 26 '26 22:01

Oliv



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!