Suppose I define a type
data A a = A a | B deriving Show
I know that (B :: A Int) == (B :: A Double)
does not typecheck because A Int
and A Double
are different, unequal types, so I can't apply (==) :: Eq a => a -> a -> Bool
But then I can ask ghci what is show B
, and ghci says it is the string "B". What exactly is the type of that B
? Is it A Int
? Why? And why does ghci not complain that the type of B
is ambiguous, given that it can be A a
for absolutely any a
.
I can similarly ask ghci what is show (B==B)
, and it says "True", what is the type of both those B
's?
When I ask ghci the type of B with :t B
, it prints B :: A a
, but unless I am confused in the two examples above it must be some specific type without any type parameters. So how do I find out what the type of B
in B==B
is?
I'm confused a little. Is this described anywhere?
The reason for the behaviour is an ghc extension that is called ExtendedDefaultRules.
Quoting from the link:
However, it is tiresome for the user to have to specify the type, so GHCi extends Haskell's type-defaulting rules (Section 4.3.4 of the Haskell 2010 Report) as follows. The standard rules take each group of constraints (C1 a, C2 a, ..., Cn a) for each type variable a, and defaults the type variable if
- The type variable a appears in no other constraints
- All the classes Ci are standard.
- At least one of the classes Ci is numeric.
At the GHCi prompt, or with GHC if the -XExtendedDefaultRules flag is given, the following additional differences apply:
- Rule 2 above is relaxed thus: All of the classes Ci are single-parameter type classes.
- Rule 3 above is relaxed this: At least one of the classes Ci is numeric, or is Show, Eq, or Ord. The unit type () is added to the start of the standard list of types which are tried when doing type defaulting.
So according to these rules, in B == B
or show B
, ()
is picked for a
.
You can also test this by doing the following at the GHCi prompt:
:set -XNoExtendedDefaultRules
data Foo a = A a | B deriving Eq
B == B
which results in the expected ambiguous type variable a
error.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With