LYR-SEM0092
inference through a type that conforms twice
A generic call infers a type argument from an argument's conformance to an interface, and the argument's type conforms to that interface more than once with different type arguments.
Explanation
When a parameter's type is an interface instance such as Source<T>, T is read from the argument type's conformance. A type conforming as both Source<int> and Source<string> gives two answers, and the order of the conformances must never decide a call.
Write the type argument explicitly: take<int>(…).
Wrong
interface Source<T> {
fn get(): T;
}
struct Both {
n: int,
}
extend Both :: [Source<int>] {
fn get(): int { return this.n; }
}
extend Both :: [Source<string>] {
fn get(): string { return "n"; }
}
fn take<T>(s: Source<T>): T {
return s.get();
}
fn main(): void {
let _ = take(Both { n = 1 });
}
Right
interface Source<T> {
fn get(): T;
}
struct Both {
n: int,
}
extend Both :: [Source<int>] {
fn get(): int { return this.n; }
}
extend Both :: [Source<string>] {
fn get(): string { return "n"; }
}
fn take<T>(s: Source<T>): T {
return s.get();
}
fn main(): void {
let _ = take<int>(Both { n = 1 });
}