github.com/JimmyHuang454/JLS-go@v0.0.0-20230831150107-90d536585ba0/internal/types/testdata/check/issues1.go (about) 1 // -oldComparableSemantics 2 3 // Copyright 2020 The Go Authors. All rights reserved. 4 // Use of this source code is governed by a BSD-style 5 // license that can be found in the LICENSE file. 6 7 // This file contains regression tests for bugs found. 8 9 package p 10 11 import "io" 12 import "context" 13 14 func eql[T comparable](x, y T) bool { 15 return x == y 16 } 17 18 func _[X comparable, Y interface{comparable; m()}]() { 19 var x X 20 var y Y 21 eql(x, y /* ERROR does not match */ ) // interfaces of different types 22 eql(x, x) 23 eql(y, y) 24 eql(y, nil /* ERROR cannot use nil as Y value in argument to eql */ ) 25 eql[io /* ERROR does not satisfy comparable */ .Reader](nil, nil) 26 } 27 28 // If we have a receiver of pointer to type parameter type (below: *T) 29 // we don't have any methods, like for interfaces. 30 type C[T any] interface { 31 m() 32 } 33 34 // using type bound C 35 func _[T C[T]](x *T) { 36 x.m /* ERROR x\.m undefined */ () 37 } 38 39 // using an interface literal as bound 40 func _[T interface{ m() }](x *T) { 41 x.m /* ERROR x\.m undefined */ () 42 } 43 44 func f2[_ interface{ m1(); m2() }]() {} 45 46 type T struct{} 47 func (T) m1() 48 func (*T) m2() 49 50 func _() { 51 f2[T /* ERROR m2 has pointer receiver */ ]() 52 f2[*T]() 53 } 54 55 // When a type parameter is used as an argument to instantiate a parameterized 56 // type, the type argument's type set must be a subset of the instantiated type 57 // parameter's type set. 58 type T1[P interface{~uint}] struct{} 59 60 func _[P any]() { 61 _ = T1[P /* ERROR P does not satisfy interface{~uint} */ ]{} 62 } 63 64 // This is the original (simplified) program causing the same issue. 65 type Unsigned interface { 66 ~uint 67 } 68 69 type T2[U Unsigned] struct { 70 s U 71 } 72 73 func (u T2[U]) Add1() U { 74 return u.s + 1 75 } 76 77 func NewT2[U any]() T2[U /* ERROR U does not satisfy Unsigned */ ] { 78 return T2[U /* ERROR U does not satisfy Unsigned */ ]{} 79 } 80 81 func _() { 82 u := NewT2[string]() 83 _ = u.Add1() 84 } 85 86 // When we encounter an instantiated type such as Elem[T] we must 87 // not "expand" the instantiation when the type to be instantiated 88 // (Elem in this case) is not yet fully set up. 89 type Elem[T any] struct { 90 next *Elem[T] 91 list *List[T] 92 } 93 94 type List[T any] struct { 95 root Elem[T] 96 } 97 98 func (l *List[T]) Init() { 99 l.root.next = &l.root 100 } 101 102 // This is the original program causing the same issue. 103 type Element2[TElem any] struct { 104 next, prev *Element2[TElem] 105 list *List2[TElem] 106 Value TElem 107 } 108 109 type List2[TElem any] struct { 110 root Element2[TElem] 111 len int 112 } 113 114 func (l *List2[TElem]) Init() *List2[TElem] { 115 l.root.next = &l.root 116 l.root.prev = &l.root 117 l.len = 0 118 return l 119 } 120 121 // Self-recursive instantiations must work correctly. 122 type A[P any] struct { _ *A[P] } 123 124 type AB[P any] struct { _ *BA[P] } 125 type BA[P any] struct { _ *AB[P] } 126 127 // And a variation that also caused a problem with an 128 // unresolved underlying type. 129 type Element3[TElem any] struct { 130 next, prev *Element3[TElem] 131 list *List3[TElem] 132 Value TElem 133 } 134 135 func (e *Element3[TElem]) Next() *Element3[TElem] { 136 if p := e.next; e.list != nil && p != &e.list.root { 137 return p 138 } 139 return nil 140 } 141 142 type List3[TElem any] struct { 143 root Element3[TElem] 144 len int 145 } 146 147 // Infinite generic type declarations must lead to an error. 148 type inf1[T any] struct{ _ inf1 /* ERROR invalid recursive type */ [T] } 149 type inf2[T any] struct{ inf2 /* ERROR invalid recursive type */ [T] } 150 151 // The implementation of conversions T(x) between integers and floating-point 152 // numbers checks that both T and x have either integer or floating-point 153 // type. When the type of T or x is a type parameter, the respective simple 154 // predicate disjunction in the implementation was wrong because if a type set 155 // contains both an integer and a floating-point type, the type parameter is 156 // neither an integer or a floating-point number. 157 func convert[T1, T2 interface{~int | ~uint | ~float32}](v T1) T2 { 158 return T2(v) 159 } 160 161 func _() { 162 convert[int, uint](5) 163 } 164 165 // When testing binary operators, for +, the operand types must either be 166 // both numeric, or both strings. The implementation had the same problem 167 // with this check as the conversion issue above (issue #39623). 168 169 func issue39623[T interface{~int | ~string}](x, y T) T { 170 return x + y 171 } 172 173 // Simplified, from https://go2goplay.golang.org/p/efS6x6s-9NI: 174 func Sum[T interface{~int | ~string}](s []T) (sum T) { 175 for _, v := range s { 176 sum += v 177 } 178 return 179 } 180 181 // Assignability of an unnamed pointer type to a type parameter that 182 // has a matching underlying type. 183 func _[T interface{}, PT interface{~*T}] (x T) PT { 184 return &x 185 } 186 187 // Indexing of type parameters containing type parameters in their constraint terms: 188 func at[T interface{ ~[]E }, E interface{}](x T, i int) E { 189 return x[i] 190 } 191 192 // Conversion of a local type to a type parameter. 193 func _[T interface{~int}](x T) { 194 type myint int 195 var _ int = int(x) 196 var _ T = 42 197 var _ T = T(myint(42)) 198 } 199 200 // Indexing a type parameter with an array type bound checks length. 201 // (Example by mdempsky@.) 202 func _[T interface { ~[10]int }](x T) { 203 _ = x[9] // ok 204 _ = x[20 /* ERROR out of bounds */ ] 205 } 206 207 // Pointer indirection of a type parameter. 208 func _[T interface{ ~*int }](p T) int { 209 return *p 210 } 211 212 // Channel sends and receives on type parameters. 213 func _[T interface{ ~chan int }](ch T) int { 214 ch <- 0 215 return <- ch 216 } 217 218 // Calling of a generic variable. 219 func _[T interface{ ~func() }](f T) { 220 f() 221 go f() 222 } 223 224 type F1 func() 225 type F2 func() 226 func _[T interface{ func()|F1|F2 }](f T) { 227 f() 228 go f() 229 } 230 231 // We must compare against the (possibly underlying) types of term list 232 // elements when checking if a constraint is satisfied by a type. 233 // The underlying type of each term must be computed after the 234 // interface has been instantiated as its constraint may contain 235 // a type parameter that was substituted with a defined type. 236 // Test case from an (originally) failing example. 237 238 type sliceOf[E any] interface{ ~[]E } 239 240 func append[T interface{}, S sliceOf[T], T2 interface{}](s S, t ...T2) S { panic(0) } 241 242 var f func() 243 var cancelSlice []context.CancelFunc 244 var _ = append[context.CancelFunc, []context.CancelFunc, context.CancelFunc](cancelSlice, f) 245 246 // A generic function must be instantiated with a type, not a value. 247 248 func g[T any](T) T { panic(0) } 249 250 var _ = g[int] 251 var _ = g[nil /* ERROR is not a type */ ] 252 var _ = g(0)