Уважаемые эксперты Haskell / GHC,
Я действительно не понимаю, почему GHC сообщает о перекрывающихся экземплярах, в то время как только один действителен в соответствии с предоставленными контекстами. Например, давайте рассмотрим следующий фрагмент кода:
{-# LANGUAGE FlexibleInstances #-}
class C a where
foo :: a -> String
foo x = "OK"
instance C Bool
instance (C a) => C [a]
instance (C a) => C [(Char, a)]
main = print $ foo [('a', True)]
Компиляция дает:
Test.hs:13:16: error:
* Overlapping instances for C [(Char, Bool)]
arising from a use of `foo'
Matching instances:
instance C a => C [a] -- Defined at Test.hs:9:10
instance C a => C [(Char, a)] -- Defined at Test.hs:11:10
* In the second argument of `($)', namely `foo [('a', True)]'
In the expression: print $ foo [('a', True)]
In an equation for `main': main = print $ foo [('a', True)]
Дело в том, что ('a', True)
имеет тип (Char, Bool)
, который не является экземпляром C
. Следовательно, instance C a => C [a]
не применяется к значению [('a', True)]
.
Поэтому почему GHC рассматривает это?
Вопрос действительно в понимании поведения GHC, а не в том, как избежать проблемы (например, используя OverlappingInstances
). Это потому, что контексты не используются при «разрешении» вызова функции? И если да, то почему?
Заранее спасибо!