@@ -33,6 +33,7 @@ import annotation.tailrec
33
33
import Flags .FlagSet
34
34
import typer .Mode
35
35
import language .implicitConversions
36
+ import scala .util .hashing .{ MurmurHash3 => hashing }
36
37
37
38
object Types {
38
39
@@ -2249,12 +2250,14 @@ object Types {
2249
2250
}
2250
2251
}
2251
2252
2252
- case class PolyType (paramNames : List [TypeName ])(paramBoundsExp : PolyType => List [TypeBounds ], resultTypeExp : PolyType => Type )
2253
+ abstract case class PolyType (paramNames : List [TypeName ])(paramBoundsExp : PolyType => List [TypeBounds ], resultTypeExp : PolyType => Type )
2253
2254
extends CachedGroundType with BindingType with TermType with MethodOrPoly {
2254
2255
2255
2256
val paramBounds = paramBoundsExp(this )
2256
2257
val resType = resultTypeExp(this )
2257
2258
2259
+ assert(resType ne null )
2260
+
2258
2261
override def resultType (implicit ctx : Context ) = resType
2259
2262
2260
2263
protected def computeSignature (implicit ctx : Context ) = resultSignature
@@ -2276,13 +2279,26 @@ object Types {
2276
2279
2277
2280
// need to override hashCode and equals to be object identity
2278
2281
// because paramNames by itself is not discriminatory enough
2279
- override def equals (other : Any ) = this eq other.asInstanceOf [AnyRef ]
2280
- override def computeHash = identityHash
2282
+ override def equals (other : Any ) = other match {
2283
+ case other : PolyType =>
2284
+ other.paramNames == this .paramNames && other.paramBounds == this .paramBounds && other.resType == this .resType
2285
+ case _ => false
2286
+ }
2287
+ override def computeHash = {
2288
+ doHash(paramNames, resType, paramBounds)
2289
+ }
2281
2290
2282
2291
override def toString = s " PolyType( $paramNames, $paramBounds, $resType) "
2283
2292
}
2284
2293
2294
+ class CachedPolyType (paramNames : List [TypeName ])(paramBoundsExp : PolyType => List [TypeBounds ], resultTypeExp : PolyType => Type )
2295
+ extends PolyType (paramNames)(paramBoundsExp, resultTypeExp)
2296
+
2285
2297
object PolyType {
2298
+ def apply (paramNames : List [TypeName ])(paramBoundsExp : PolyType => List [TypeBounds ], resultTypeExp : PolyType => Type )(implicit ctx : Context ): PolyType = {
2299
+ unique(new CachedPolyType (paramNames)(paramBoundsExp, resultTypeExp))
2300
+ }
2301
+
2286
2302
def fromSymbols (tparams : List [Symbol ], resultType : Type )(implicit ctx : Context ) =
2287
2303
if (tparams.isEmpty) resultType
2288
2304
else {
@@ -2358,7 +2374,7 @@ object Types {
2358
2374
// no customized hashCode/equals needed because cycle is broken in PolyType
2359
2375
override def toString = s " PolyParam( ${binder.paramNames(paramNum)}) "
2360
2376
2361
- override def computeHash = doHash( paramNum, binder)
2377
+ override def computeHash = finishHash(hashing.mix(hashing.mix(hashSeed, paramNum) , binder.identityHash), 1 )
2362
2378
override def equals (that : Any ) = that match {
2363
2379
case that : PolyParam =>
2364
2380
(this .binder eq that.binder) && this .paramNum == that.paramNum
0 commit comments