On Tue, Sep 8, 2020 at 9:25 PM Ian Lance Taylor <i...@golang.org> wrote:

>
> I think that it's really crucial for type inference rules to be as simple
> and clear as possible.  There must never be any confusion as to what an
> inferred type might be.  In complicated cases, it's fine to explicitly list
> the type arguments.  In fact, it's more than fine: it's desirable.
>

This doesn't seem to be a complicated case. We just have a type parameter
that needs pointer methods in order to be passed to another function. I
wouldn't suggest making the inference rules more clever to compensate for
this case. As I mentioned, the compiler probably shouldn't be smart enough
to figure this out as written.

I think the difficulty is coming from conflicting requirements. For element
type inference, you want the freedom to be able to provide arbitrary named
composite types as arguments and get the element type based on structural
matching. But for derived type constraints, you really actually don't want
that extra degree of freedom in the identity of the composite type.
Instead, you want to constrain the specific derived type. Maybe it would be
better to allow derived types to be constrained directly:

https://go2goplay.golang.org/p/cLVkk4HGWre

type Constraint interface{
Method()
}

func Foo[T any, *T Constraint](_ T) {}

func Bar[T any, *T Constraint](t T) {
Foo(t)
}

It might seem weird to have a "parameter" which has to be a specific type
in relation to other parameters, but that's already what was happening with
constraint type inference. This is sort of similar to the original idea of
having pointer type constraints, except you need both T and *T as
parameters, with each being constrained separately.

This doesn't cover the use case of accepting named slice types and
inferring the element type, so constraint type inference would still be
needed. Of course, part of what makes constraint type inference appealing
is that it gets two birds with one stone, but it seems like the conflicting
requirements of the two use cases is undermining the value of both.

On Tue, Sep 8, 2020 at 9:25 PM Ian Lance Taylor <i...@golang.org> wrote:

> On Tue, Sep 8, 2020 at 5:47 PM Steven Blenkinsop <steven...@gmail.com>
> wrote:
>
> >
>
> > Reading over the pointer method example, I noticed that a derived type
> cannot be inferred in a nested call while leaving method constraints intact:
>
> >
>
> > type DerivedTypeConstraint[T any] interface {
>
> > type *T
>
> > Method()
>
> > }
>
> >
>
> > func Foo[T any, PT DerivedTypeConstraint[T]](_ T) {}
>
> >
>
> > func Bar[T any, PT DerivedTypeConstraint[T]](t T) {
>
> > Foo(t) // Error: *T has no methods
>
> > }
>
> >
>
> > type S struct{}
>
> >
>
> > func (S) Method() {}
>
> >
>
> > func main() {
>
> > Bar(S{}) // This is fine, PT gets inferred as *S, which implements Method
>
> > }
>
> >
>
> >
>
> > https://go2goplay.golang.org/p/9GMdhTbcMDs
>
> >
>
> > Obviously, you can work around this by passing PT explicitly rather than
> letting *T be inferred. It's just unfortunate that, even though *T must
> have any methods in the constraint on PT (any other type with the same
> underlying type would have no methods), the compiler isn't, and most likely
> shouldn't be, smart enough to figure that out. I'm not sure how to solve
> this, but I think it makes the design feel a little less polished.
>
>
>
> I think that it's really crucial for type inference rules to be as
>
> simple and clear as possible.  There must never be any confusion as to
>
> what an inferred type might be.  In complicated cases, it's fine to
>
> explicitly list the type arguments.  In fact, it's more than fine:
>
> it's desirable.
>
>
>
> Ian
>
>

-- 
You received this message because you are subscribed to the Google Groups 
"golang-nuts" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to golang-nuts+unsubscr...@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/golang-nuts/CANjmGJuAZv7AJ-mrBAmOENYj%3Dtn0NmmMtDPmY%2B_BeOuZEO1ACQ%40mail.gmail.com.

Reply via email to