Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[dcl.init.general] Remove confusing ‘no initialization’ from default-initialization and zero-initialization #4910

Closed
geryogam opened this issue Sep 16, 2021 · 6 comments

Comments

@geryogam
Copy link
Contributor

From [dcl.init.general/7] (bold emphasis mine):

To default-initialize an object of type T means:

  • If T is a (possibly cv-qualified) class type ([class]), constructors are considered. The applicable constructors are enumerated ([over.match.ctor]), and the best one for the initializer () is chosen through overload resolution ([over.match]). The constructor thus selected is called, with an empty argument list, to initialize the object.
  • If T is an array type, each element is default-initialized.
  • Otherwise, no initialization is performed.

How can a scalar object be at the same time default-initialized and not initialized?

For instance consider this program:

int main() {
    int i;
    return 0;
}

From [dcl.init.general/11]:

If no initializer is specified for an object, the object is default-initialized.

So i is default-initialized.

From [basic.life/1]:

A variable is said to have vacuous initialization if it is default-initialized and, if it is of class type or a (possibly multi-dimensional) array thereof, that class type has a trivial default constructor. The lifetime of an object of type T begins when:

  • storage with the proper alignment and size for type T is obtained, and
  • its initialization (if any) is complete (including vacuous initialization) ([dcl.init]),

So i is a vacuous initialization and therefore its lifetime begins. Yet i is uninitialized so its lifetime does not begin.

Therefore I suggest we reword [dcl.init.general/7] from

  • Otherwise, no initialization is performed.

to

  • Otherwise, nothing is performed.

That way scalar types are not in two different states at the same time.

Same remark for [dcl.init.general/6] (bold emphasis mine):

To zero-initialize an object or reference of type T means:

  • if T is a scalar type, the object is initialized to the value obtained by converting the integer literal 0 (zero) to T;86
  • if T is a (possibly cv-qualified) non-union class type, its padding bits are initialized to zero bits and each non-static data member, each non-virtual base class subobject, and, if the object is not a base class subobject, each virtual base class subobject is zero-initialized;
  • if T is a (possibly cv-qualified) union type, its padding bits are initialized to zero bits and the object's first non-static named data member is zero-initialized;
  • if T is an array type, each element is zero-initialized;
  • if T is a reference type, no initialization is performed.

How can a reference be at the same time zero-initialized and not initialized?

Therefore I suggest we reword [dcl.init.general/6] from

  • if T is a reference type, no initialization is performed.

to

  • if T is a reference type, nothing is performed.
@jwakely
Copy link
Member

jwakely commented Sep 16, 2021

Yet i is uninitialized so its lifetime does not begin.

Wrong.

Its lifetime begins when storage is obtained, and initialization if any is complete.

If no initialization occurs, the lifetime still begins.

@jwakely
Copy link
Member

jwakely commented Sep 16, 2021

How can a reference be at the same time zero-initialized and not initialized?

Because zero-initialization is a blanket term for several different effects, depending on the type. One of those is "no initialization". It's not terribly important for a reference anyway, because that would be ill-formed (references must be bound to something).

Please use stack overflow for help reading the wording, not this issue tracker.

@geryogam
Copy link
Contributor Author

geryogam commented Sep 16, 2021

Because zero-initialization is a blanket term for several different effects, depending on the type. One of those is "no initialization".

Alright. In other words:

  • an uninitialized reference is considered zero-initialized;
  • an uninitialized scalar is considered default-initialized;
  • any other uninitialized entity is not considered zero-initialized nor default-initialized.

Correct?

@jensmaurer
Copy link
Member

This is not the C++ help desk.

@jwakely
Copy link
Member

jwakely commented Sep 16, 2021

Correct?

No.

@geryogam
Copy link
Contributor Author

Please use stack overflow for help reading the wording, not this issue tracker.

Alright, I have just asked the question here since it is more appropriate:
https://stackoverflow.com/q/69206296/2326961

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants