blob: 91f9df1d840d0460846f9f98f47306f6ce5a6332 [file] [log] [blame]
// Copyright 2023 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// This file shows some examples of "reverse" type inference
// where the type arguments for generic functions are determined
// from assigning the functions.
package p
func f1[P any](P) {}
func f2[P any]() P { var x P; return x }
func f3[P, Q any](P) Q { var x Q; return x }
func f4[P any](P, P) {}
func f5[P any](P) []P { return nil }
func f6[P any](int) P { var x P; return x }
func f7[P any](P) string { return "" }
// initialization expressions
var (
v1 = f1 // ERROR "cannot use generic function f1 without instantiation"
v2 func(int) = f2 // ERROR "cannot infer P"
v3 func(int) = f1
v4 func() int = f2
v5 func(int) int = f3
_ func(int) int = f3[int]
v6 func(int, int) = f4
v7 func(int, string) = f4 // ERROR "inferred type func(int, int) for func(P, P) does not match type func(int, string) of v7"
v8 func(int) []int = f5
v9 func(string) []int = f5 // ERROR "inferred type func(string) []string for func(P) []P does not match type func(string) []int of v9"
_, _ func(int) = f1, f1
_, _ func(int) = f1, f2 // ERROR "cannot infer P"
)
// Regular assignments
func _() {
v1 = f1 // no error here because v1 is invalid (we don't know its type) due to the error above
var v1_ func() int
_ = v1_
v1_ = f1 // ERROR "cannot infer P"
v2 = f2 // ERROR "cannot infer P"
v3 = f1
v4 = f2
v5 = f3
v5 = f3[int]
v6 = f4
v7 = f4 // ERROR "inferred type func(int, int) for func(P, P) does not match type func(int, string) of v7"
v8 = f5
v9 = f5 // ERROR "inferred type func(string) []string for func(P) []P does not match type func(string) []int of v9"
// non-trivial LHS
var a [2]func(string) []int
a[0] = f5 // ERROR "inferred type func(string) []string for func(P) []P does not match type func(string) []int of a[0]"
}
// Return statements
func _() func(int) { return f1 }
func _() func() int { return f2 }
func _() func(int) int { return f3 }
func _() func(int) int { return f3[int] }
func _() func(int, int) { return f4 }
func _() func(int, string) {
return f4 /* ERROR "inferred type func(int, int) for func(P, P) does not match type func(int, string) of result variable" */
}
func _() func(int) []int { return f5 }
func _() func(string) []int {
return f5 /* ERROR "inferred type func(string) []string for func(P) []P does not match type func(string) []int of result variable" */
}
func _() (_, _ func(int)) { return f1, f1 }
func _() (_, _ func(int)) { return f1, f2 /* ERROR "cannot infer P" */ }
// Argument passing
func g1(func(int)) {}
func g2(func(int, int)) {}
func g3(func(int) string) {}
func g4[P any](func(P) string) {}
func g5[P, Q any](func(P) string, func(P) Q) {}
func g6(func(int), func(string)) {}
func _() {
g1(f1)
g1(f2 /* ERROR "cannot infer P" */)
g2(f4)
g4(f6)
g5(f6, f7)
g6(f1, f1)
}
// Argument passing of partially instantiated functions
func h(func(int, string), func(string, int)) {}
func p[P, Q any](P, Q) {}
func _() {
h(p, p)
h(p[int], p[string])
}