C++ Logo


Advanced search

Re: is_complete type trait?

From: Arthur O'Dwyer <arthur.j.odwyer_at_[hidden]>
Date: Fri, 12 Nov 2021 12:04:41 -0500
On Fri, Nov 12, 2021 at 8:07 AM Lénárd Szolnoki via Std-Proposals <
std-proposals_at_[hidden]> wrote:

> On Fri, 12 Nov 2021 00:50:21 +0100
> Bjorn Reese via Std-Proposals <std-proposals_at_[hidden]> wrote:
> > Has there been any proposals to add a type trait to check if a type
> > is complete?
> I mainly agree with others that this is a footgun and it simply can't
> be standardized at least in the same form as the other traits.

I also agree that it shouldn't be standardized, because footgun.
Also, notice that almost always, when you think you want a complete type,
really what you want is a complete *object* type (not a reference type and
not a function type). So merely something like `concept std::complete`
wouldn't be completely what you want, either in the STL or in your own code.

However, I have become ambivalent on the footgun argument, because it
actually applies to many Ranges concepts that are even more complicated
than `is_complete`, and yet we standardized those. Consider e.g.

struct S;
inline bool obviously_false() { return std::ranges::view<S>; }

struct S : std::string_view {};

constexpr bool std::ranges::enable_view<S> = true;


This is a hard error on GCC, and compiles without errors on Clang and MSVC.

I suspect that it's possible to construct (or run-into-in-the-wild) some
less contrived examples of this; maybe by using CRTP base classes; or
having member functions that return types like
`std::ranges::filter_view<Myself>`, where, as a side effect of naming that
type, some concept such as `view<Myself>` is prematurely "locked in" with
the wrong value. I would be interested in seeing such examples, if anyone
runs into one.

I also think that, like a lot of stuff in Ranges, this is probably "not a
problem" if you look at it from exactly the right angle. Ranges has lots of
new idioms that you have to look at in exactly the right way for them to
make sense, e.g.
- always pass ranges by forwarding-reference (but do not forward them)
- in particular, never pass by const-reference
- yes dangling is a problem, but you can mitigate that by never prematurely
dissecting a range object into an iterator-pair
- yes prematurely "locking in" concepts is a problem, but you can mitigate
that by... (fill in the blank)
Therefore I suspect that having a `std::complete_object_type` concept is no
bigger of a problem than `concept std::ranges::view` — either they are both
problematic, or neither of them is problematic. My current understanding is
that they're both problematic; but I suspect that there's someone out
there, more up on their Ranges idioms, who could explain why* if you look
at it from the right angle* neither of them is problematic, and could give
some best practices for dealing with them both.

my $.02,

Received on 2021-11-12 11:04:54