@@ -1105,44 +1105,18 @@ object Types {
11051105 def widenUnion (implicit ctx : Context ): Type = {
11061106 widen match {
11071107 case tp @ OrType (lhs, rhs) =>
1108- def defaultJoin (tp1 : Type , tp2 : Type ) =
1109- ctx.typeComparer.lub(tp1, tp2, canConstrain = true ) match {
1110- case union : OrType => union.join
1111- case res => res
1112- }
1113-
1114- // Given a type `tpe`, if it is already a nullable union, return it unchanged.
1115- // Otherwise, construct a nullable union where `tpe` is the lhs (use `orig` to
1116- // potentially avoid creating a new object for the union).
1117- def ensureNullableUnion (tpe : Type , orig : OrType ): Type = tpe match {
1118- case orTpe : OrType if orTpe.tp2.isNullType => tpe
1119- case _ => orig.derivedOrType(tpe, defn.NullType )
1120- }
1121-
1122- // Test for nullable union that assumes the type has already been normalized.
1123- def isNullableUnionFast (tp : Type ): Boolean = tp match {
1124- case orTpe : OrType if orTpe.tp2.isNullType => true
1125- case _ => false
1126- }
1127-
1128- if (ctx.explicitNulls) {
1129- // Don't widen `T|Null`, since otherwise we wouldn't be able to infer nullable unions.
1130- // This part relies on the postcondition of widenUnion: the result is either a
1131- // non-union type, or a nullable union type where the rhs is `Null` type.
1132- if (rhs.isNullType) ensureNullableUnion(lhs.widenUnion, tp)
1133- else if (lhs.isNullType) ensureNullableUnion(rhs.widenUnion, tp)
1134- else {
1135- val lhsWiden = lhs.widenUnion
1136- val rhsWiden = rhs.widenUnion
1137- val tmpRes = defaultJoin(lhs.widenUnion, rhs.widenUnion)
1138- if (isNullableUnionFast(lhsWiden) || isNullableUnionFast(rhsWiden))
1139- // If either lhs or rhs is a nullable union,
1140- // we need to ensure the result is also a nullable union.
1141- ensureNullableUnion(tmpRes, tp)
1142- else tmpRes
1143- }
1108+ tp match {
1109+ case OrNull (tp1) =>
1110+ // Don't widen `T|Null`, since otherwise we wouldn't be able to infer nullable unions.
1111+ val tp1Widen = tp1.widenUnion
1112+ if (tp1Widen.isRef(defn.AnyClass )) tp1Widen
1113+ else tp.derivedOrType(tp1Widen, defn.NullType )
1114+ case _ =>
1115+ ctx.typeComparer.lub(lhs.widenUnion, rhs.widenUnion, canConstrain = true ) match {
1116+ case union : OrType => union.join
1117+ case res => res
1118+ }
11441119 }
1145- else defaultJoin(lhs.widenUnion, rhs.widenUnion)
11461120 case tp @ AndType (tp1, tp2) =>
11471121 tp derived_& (tp1.widenUnion, tp2.widenUnion)
11481122 case tp : RefinedType =>
@@ -2965,9 +2939,12 @@ object Types {
29652939 object OrNull {
29662940 def apply (tp : Type )(given Context ) =
29672941 OrType (tp, defn.NullType )
2968- def unapply (tp : Type )(given Context ): Option [Type ] =
2942+ def unapply (tp : Type )(given ctx : Context ): Option [Type ] =
2943+ if (ctx.explicitNulls) {
29692944 val tp1 = tp.stripNull
29702945 if tp1 ne tp then Some (tp1) else None
2946+ }
2947+ else None
29712948 }
29722949
29732950 object OrJavaNull {
0 commit comments