C++ Logo

std-proposals

Advanced search

Re: [std-proposals] [PXXXXR0] Add a New Keyword `undecl`

From: Sebastian Wittmeier <wittmeier_at_[hidden]>
Date: Wed, 10 Dec 2025 23:28:05 +0100
About extending the lifetime with span & co. std::span is non-owning, in your idea the lifetime would be extended as long as the std::span view lives What happens, if you take a subspan and drop the span? Will the subspan inherit the relationship to the original std::vector? Where is the bookkeeping without the type knowing?   I think in practice this would not work.     -----Ursprüngliche Nachricht----- Von:Jarrad Waterloo via Std-Proposals <std-proposals_at_[hidden]> Gesendet:Mi 10.12.2025 22:20 Betreff:Re: [std-proposals] [PXXXXR0] Add a New Keyword `undecl` An:std-proposals_at_[hidden]; CC:Jarrad Waterloo <descender76_at_[hidden]>; I'd like to summarize a few points in case they have been missed.  `undecl`, to some, seems like it is solving half of a problem It might be good if there were the following two versions of it instead:  undecl(destroy) //  as the undecl author envisioned it undecl(hide) // as it is related to shadowing but not shadowing  Likely neither `destroy` nor `hide` should be the default. So don't waste 10 years debating the default when you can have 10 years of explicit usage telling us what the default will be.  The following does not involve any shadowing though it is related to shadowing and undecl(hide).  string_view a = string{};// immediate dangling //or span a = vector{};// immediate dangling  The defensive programming workaround is as follows.  struct dename{}; // simply any 0 size tag type without any functionality will do ... ... ... vector some_name_we_will_only_use_once{}; span a = some_name_we_will_only_use_once; {     dename some_name_we_will_only_use_once;     // MOVE all other code into this block }  OR with undecl(hide)  vector some_name_we_will_only_use_once{}; span a = some_name_we_will_only_use_once; undecl(hide) some_name_we_will_only_use_once;  NOTE: The current status quo of `span a = vector{};` is that programmers either immediately dangle OR have to write verbose code OR worse lazily have superfluous aliases out there contributing to invalidation, concurrency errors and/or harder to understand code.  Making `span a = vector{};` NOT immediate dangling BY allowing lifetime extension to apply to all pure alias types instead of just references DOESN'T break any existing code which isn't already immediately dangling and it doesn't require any new keywords or annotations. Rather it has numerous benefits.  This would remove an embarrassing form of dangling associated with the creation of temporaries. This would remove an inconsistency that lifetime extension works on reference but not reference like types. This allows the programmer to better manage invalidation without having to create superfluous aliases that only further enable invalidation.   On Wed, Dec 10, 2025 at 3:14 PM Simon Schröder via Std-Proposals <std-proposals_at_[hidden] <mailto:std-proposals_at_[hidden]> > wrote: > On Dec 10, 2025, at 9:46 AM, David Brown via Std-Proposals <std-proposals_at_[hidden] <mailto:std-proposals_at_[hidden]> > wrote: > > 1. Copy-and-paste code (redeclaration without undecl) : This variant I don’t really like. It would be too easy to accidentally shadow a variable. If I have working code and I accidentally redeclare a variable (possibly with the same type) right between the declaration of the old variable and the previously last use of the variable, I will break that code without a compiler error. In my opinion it is a good thing to have compiler errors when you try to do something stupid. (Maybe we could allow shadowing without undecl and then unshadow using undecl. Anyway, it would be much better if you’d had to be explicit about shadowing, e.g. with an attribute [[shadow]]. Nothing accidental about that.) BTW, if you want a variable you can shadow, use _. > > 2. Explicitly ending the lifetime of a variable and making it unusable: > Other languages (e.g. Rust) use the ‘keyword’ ‘drop’ for this. I’m not sure if ‘drop’ will collide with common variable names (or more likely with function names). ‘undecl’ certainly looks like it is not yet used in any C++ code. As has been replied already: std::optional already allows to end the lifetime of a variable early (but without the added “benefit” of being able to reuse its name (if it’s not the same type)). > > 3. Const-locking identifiers (redeclaration without undecl) : > This is a nice idea I could get behind. > >    auto x = get_x(); >    change_x(&x); >    const auto x = x; >    change_x(&x);        // Compile-time error > Currently syntax like the line const auto x = x; would first declare a variable ‘x’ and then assign it to itself. We should have some other syntax for this feature. It is currently already possible to write this kind of buggy code if ‘x’ comes from an outer scope. There is no reason for this to behave differently if we shadow an ‘x’ from the same scope. And certainly someone is “relying” on this bug and we’d break someone’s code if we fix this. -- Std-Proposals mailing list Std-Proposals_at_[hidden] <mailto:Std-Proposals_at_[hidden]> https://lists.isocpp.org/mailman/listinfo.cgi/std-proposals -- Std-Proposals mailing list Std-Proposals_at_[hidden] https://lists.isocpp.org/mailman/listinfo.cgi/std-proposals  

Received on 2025-12-10 22:42:50