Это было вызвано разрешением типа 'f = f (<*>) pure', в котором обсуждается более сложный пример, но этот тоже работает.
Следующее определение компилируется без проблем:
w :: Integral a => a
w = fromInteger w
... Конечно, это не работает во время выполнения, но это помимо вопроса. Дело в том, что само определение w
использует специализированную версию w :: Integer
. Понятно, что это подходящая реализация, и, следовательно, проверки типов.
Однако, если мы удалим подпись, то GHC выведет не вышеуказанный тип, а только конкретный:
w' = fromInteger w'
GHCi> :t w
w :: Integral a => a
GHCi> :t w'
w' :: Integer
Ну, когда я увидел это, я был совершенно уверен, что это ограничение мономорфизма на работе. Хорошо известно, что, например,
i = 3
GHCi> :t i
i :: Integer
хотя i :: Num p => p
было бы вполне возможно. И действительно, i :: Num p => p
выводится, если -XNoMonomorphismRestriction
активен, т.е. если ограничение мономорфизма отключено.
Однако в случае w'
выводится только тип Integer
даже когда ограничение мономорфизма отключено.
Чтобы подсчитать, что это как-то связано с дефолтом:
fromFloat :: RealFrac a => Float -> a
q :: RealFrac a => a
q = fromFloat q
q' = fromFloat q'
GHCi> :t q
q :: RealFrac a => a
GHCi> :t q'
q' :: Float
Почему полиморфный тип не выводится?