Date: Fri, 26 Jan 2024 23:17:38 +0000
> The key justification for `constinit` was avoiding the "Static
> Initialization Order Fiasco".
And that's still valid. This proposal doesn't impact the existing usage or take away from it.
> `constinit` and `override` are about preventing breakage, preventing
> scenarios that cause your code to behave incorrectly. An "expensive
> constructor" being invoked at runtime is not broken code; it's just
> *slower* code
That is fair. In the niche case that the constructor (or something using its const members) behaves differently based on whether it is constant evaluated or not, it could cause incorrect behavior.
Maybe consteval is a better example here. It similarly does not prevent incorrect code (a runtime-evaluated constexpr function will produce an error its return value is used as a compile time constant), but does guarantee code isn't evaluated at runtime unexpectedly.
________________________________
From: Std-Proposals <std-proposals-bounces_at_[hidden]> on behalf of Jason McKesson via Std-Proposals <std-proposals_at_[hidden]>
Sent: Friday, January 26, 2024 1:32:12 PM
To: std-proposals_at_[hidden]pp.org <std-proposals_at_[hidden]>
Cc: Jason McKesson <jmckesson_at_[hidden]>
Subject: Re: [std-proposals] Expanding constinit
On Fri, Jan 26, 2024 at 2:01 PM Franklin via Std-Proposals
<std-proposals_at_[hidden]> wrote:
>
> There seems to have been a lot of discussion (way more than I can reply to!), so here are my responses to some of the discussion points. Please note the quotes are paraphrased.
>
> > This is not possible because stack allocation is done at runtime
> As is constant static and thread local initialization, done at program and threat start, respectively. constinit only specifies that the value they are initialized with is a compile time constant, which is also fine with automatic storage duration
>
> > This dilutes the meaning of constinit
> Constinit, compared with constexpr and consteval, is considerably less common and only fulfills a niche purpose (globals are often considered bad practice). The changes do not modify behavior of constinit, only the conditions in which it can be used.
>
> > You can store the result of a constant expression in a separate constexpr variable and use that instead
> As can you for static variables. Since the assignment is to a constexpr value, it is also guaranteed to have constant initialization. The only drawback is that this does not prevent against typos to a non-constexpr variable for initialization.
The key justification for `constinit` was avoiding the "Static
Initialization Order Fiasco". By ensuring that a static variable
(whose initializing expressions can use other previously declared
static variables) is initialized with a constant expression, you can
guarantee that its initializing expression cannot be broken by
initialization order issues.
Using `constinit` with local variables doesn't help at all in this regard.
> The other main feature of this proposal is of course to guarantee that an expensive constructor is not invoked at runtime, which serves the same purpose as the original constinit and `override` in preventing unintentional mistakes.
`constinit` and `override` are about preventing breakage, preventing
scenarios that cause your code to behave incorrectly. An "expensive
constructor" being invoked at runtime is not broken code; it's just
*slower* code. If the constructor was `constexpr`, and the parameters
were also constant expressions, it isn't a "mistake" if the compiler
generates runtime code for it. That's a quality of implementation
matter.
--
Std-Proposals mailing list
Std-Proposals_at_[hidden]pp.org
https://lists.isocpp.org/mailman/listinfo.cgi/std-proposals
> Initialization Order Fiasco".
And that's still valid. This proposal doesn't impact the existing usage or take away from it.
> `constinit` and `override` are about preventing breakage, preventing
> scenarios that cause your code to behave incorrectly. An "expensive
> constructor" being invoked at runtime is not broken code; it's just
> *slower* code
That is fair. In the niche case that the constructor (or something using its const members) behaves differently based on whether it is constant evaluated or not, it could cause incorrect behavior.
Maybe consteval is a better example here. It similarly does not prevent incorrect code (a runtime-evaluated constexpr function will produce an error its return value is used as a compile time constant), but does guarantee code isn't evaluated at runtime unexpectedly.
________________________________
From: Std-Proposals <std-proposals-bounces_at_[hidden]> on behalf of Jason McKesson via Std-Proposals <std-proposals_at_[hidden]>
Sent: Friday, January 26, 2024 1:32:12 PM
To: std-proposals_at_[hidden]pp.org <std-proposals_at_[hidden]>
Cc: Jason McKesson <jmckesson_at_[hidden]>
Subject: Re: [std-proposals] Expanding constinit
On Fri, Jan 26, 2024 at 2:01 PM Franklin via Std-Proposals
<std-proposals_at_[hidden]> wrote:
>
> There seems to have been a lot of discussion (way more than I can reply to!), so here are my responses to some of the discussion points. Please note the quotes are paraphrased.
>
> > This is not possible because stack allocation is done at runtime
> As is constant static and thread local initialization, done at program and threat start, respectively. constinit only specifies that the value they are initialized with is a compile time constant, which is also fine with automatic storage duration
>
> > This dilutes the meaning of constinit
> Constinit, compared with constexpr and consteval, is considerably less common and only fulfills a niche purpose (globals are often considered bad practice). The changes do not modify behavior of constinit, only the conditions in which it can be used.
>
> > You can store the result of a constant expression in a separate constexpr variable and use that instead
> As can you for static variables. Since the assignment is to a constexpr value, it is also guaranteed to have constant initialization. The only drawback is that this does not prevent against typos to a non-constexpr variable for initialization.
The key justification for `constinit` was avoiding the "Static
Initialization Order Fiasco". By ensuring that a static variable
(whose initializing expressions can use other previously declared
static variables) is initialized with a constant expression, you can
guarantee that its initializing expression cannot be broken by
initialization order issues.
Using `constinit` with local variables doesn't help at all in this regard.
> The other main feature of this proposal is of course to guarantee that an expensive constructor is not invoked at runtime, which serves the same purpose as the original constinit and `override` in preventing unintentional mistakes.
`constinit` and `override` are about preventing breakage, preventing
scenarios that cause your code to behave incorrectly. An "expensive
constructor" being invoked at runtime is not broken code; it's just
*slower* code. If the constructor was `constexpr`, and the parameters
were also constant expressions, it isn't a "mistake" if the compiler
generates runtime code for it. That's a quality of implementation
matter.
--
Std-Proposals mailing list
Std-Proposals_at_[hidden]pp.org
https://lists.isocpp.org/mailman/listinfo.cgi/std-proposals
Received on 2024-01-26 23:17:42