- 
                Notifications
    You must be signed in to change notification settings 
- Fork 1.1k
Closed
Labels
Description
Minimized code
enum Bool {
  case True
  case False
}
import Bool._
enum SBool[B <: Bool] {
  case STrue extends SBool[True.type]
  case SFalse extends SBool[False.type]
}
import SBool._
type Not[B <: Bool] = B match {
  case True.type => False.type
  case False.type => True.type  
}
def not[B <: Bool](b: SBool[B]): SBool[Not[B]] = b match {
  case STrue => SFalse
  case SFalse => STrue
}Output
Found:    (SBool.STrue : SBool[(Bool.True : Bool)])
Required: SBool[Not[B]]
where:    B is a type in method not which is an alias of (Bool.False : Bool)Expectation
I would expect the not function to pass typechecking, but it doesn't. Interestingly if I add a implicitly[Not[B] =:= False.type] in the first branch of not it will not complain, so it does know that B is actually True.type in that branch and it will reduce Not correctly if I ask for it.
It looks like the types are not reduced enough when checking the type of the branches against the return type of the function (not).