Date: Thu, 6 Jan 2022 12:58:34 -0500
On Thu, Jan 6, 2022 at 11:13 AM Михаил Найденов via Std-Proposals <
std-proposals_at_[hidden]> wrote:
> Hello,
> The title says it all, consider:
>
> template<class T>
> concept stuff_as_members = requires {
> typename T::type;
> T::template templ<int>();
> };
>
> struct C
> {
> using type = int;
>
> template<class T>
> static void templ() {}
> };
>
> template<stuff_as_members T> //< constrained type!
> void func()
> {
> T::type val; //< typename should NOT be needed, type is known to be
> a typename
>
> T::templ<int>(); //< template should NOT be needed, templ is known to
> be a template
> }
>
> int main()
> {
> func<C>();
> }
>
> Can we do this for good?
>
I would guess not, because remember `typename` and `template` are hints to
the *parser* — nothing to do with semantic analysis. So the parser knows
that the token sequence
template < stuff_as_members T >
is introducing a constrained template, but it's not going to go analyze
`concept stuff_as_members` to find out what its requirements *are*. (It
might not even be allowed to do that, because the concept might have
default arguments that would need to be instantiated, and so on.
Also, there is a GCC (extension / bug) in this area, where `typename
T::type` triggers lookup *as a type* and `T::type` triggers lookup *as a
non-type*, and they both can succeed:
https://godbolt.org/z/68vx1qqMW
I believe there's at least one place in the paper standard
<https://quuxplusone.github.io/blog/2021/01/13/conversion-operator-lookup/#an-unqualified-name-that-is-a-co>
where this kind of "restricted" lookup is actually mandated (although this
simple case is not it; I'd call this a GCC bug). You'd want to check
whether your proposal would change the semantics of that kind of thing.
Basically, anything that messes with name lookup is a bad idea, and needs
motivation stronger than "hey we could do this." The motivation should be,
like, "We *should* do this *because*..." (and then insert something really
compelling).
HTH,
Arthur
std-proposals_at_[hidden]> wrote:
> Hello,
> The title says it all, consider:
>
> template<class T>
> concept stuff_as_members = requires {
> typename T::type;
> T::template templ<int>();
> };
>
> struct C
> {
> using type = int;
>
> template<class T>
> static void templ() {}
> };
>
> template<stuff_as_members T> //< constrained type!
> void func()
> {
> T::type val; //< typename should NOT be needed, type is known to be
> a typename
>
> T::templ<int>(); //< template should NOT be needed, templ is known to
> be a template
> }
>
> int main()
> {
> func<C>();
> }
>
> Can we do this for good?
>
I would guess not, because remember `typename` and `template` are hints to
the *parser* — nothing to do with semantic analysis. So the parser knows
that the token sequence
template < stuff_as_members T >
is introducing a constrained template, but it's not going to go analyze
`concept stuff_as_members` to find out what its requirements *are*. (It
might not even be allowed to do that, because the concept might have
default arguments that would need to be instantiated, and so on.
Also, there is a GCC (extension / bug) in this area, where `typename
T::type` triggers lookup *as a type* and `T::type` triggers lookup *as a
non-type*, and they both can succeed:
https://godbolt.org/z/68vx1qqMW
I believe there's at least one place in the paper standard
<https://quuxplusone.github.io/blog/2021/01/13/conversion-operator-lookup/#an-unqualified-name-that-is-a-co>
where this kind of "restricted" lookup is actually mandated (although this
simple case is not it; I'd call this a GCC bug). You'd want to check
whether your proposal would change the semantics of that kind of thing.
Basically, anything that messes with name lookup is a bad idea, and needs
motivation stronger than "hey we could do this." The motivation should be,
like, "We *should* do this *because*..." (and then insert something really
compelling).
HTH,
Arthur
Received on 2022-01-06 11:58:47