ここでは、この質問をステップバイステップで取り上げます。
のは、始めましょう:リテラルHaskell Report ...
によると
((lenDigits . factorial) 199) <= 199
整数型Integer
の適切な値に機能fromInteger
のアプリケーションを表します。私たちの最初の式が実際にあることを意味し
:
((lenDigits . factorial) (fromInteger (199 :: Integer))
<= (fromInteger (199 :: Integer))
自体によって、fromInteger (199 :: Integer)
は、ポリモーフィック型のNum a => a
を持っています。このタイプは、表現全体の文脈に特化しているかどうかを見なければなりません。その理由が見つからなくなるまで、fromInteger (199 :: Integer)
という2つの出現の多型は独立していると仮定してください(Num a => a
とNum b => b
、もしそうなら)。
lenDigits
はShow a => a -> Int
あり、そしてそう...
(lenDigits . factorial) (fromInteger (199 :: Integer))
... <=
の左側にInt
でなければなりません。 (<=)
がOrd a => a -> a -> Bool
であるとすれば、<=
の右側のfromInteger (199 :: Integer)
もInt
である必要があります。式全体は、次いで、以下のようになる。
((lenDigits . factorial) (fromInteger (199 :: Integer)) <= (199 :: Int)
第199
は最初のものはまだ多型である、Int
に特化したが。他のタイプの注釈がない場合、GHCiで式を使用すると、defaultingはInteger
に特化します。したがって、我々は、最終的に得る:第二の発現の上に今
((lenDigits . factorial) (199 :: Integer)) <= (199 :: Int)
を:
(\i -> ((lenDigits . factorial) i) <= i) 199
上記使用されたのと同じ理由により、(lenDigits . factorial) i
(<=
の左側に)Int
であるのでi
(<=
の右側にある)もInt
です。
が
((lenDigits . factorial) (199 :: Int)) <= (199 :: Int)
最初199
は今:与える、そうされていることを、私たちは...
GHCi> :t \i -> (lenDigits . factorial) i <= i
\i -> (lenDigits . factorial) i <= i :: Int -> Bool
を持っている...ので、intに(これは実際にfromInteger (199 :: Integer)
である)、それを専門と199
にそれを適用しますInteger
ではなくInt
です。 factorial (199 :: Int)
は、固定サイズInt
タイプをオーバーフローし、偽の結果につながります。最初のシナリオと同等のものを得るためにそれを回避する1つの方法は、明示的なfromInteger
を導入することになります。
GHCi> :t \i -> (lenDigits . factorial) i <= fromInteger i
\i -> (lenDigits . factorial) i <= fromInteger i :: Integer -> Bool
GHCi> (\i -> (lenDigits . factorial) i <= fromInteger i) 199
False
あなたかもしれないまた、問題の本質に取得し、すべての気まぐれを回避これら二つを比較するような'(id True、id 'a')'は大丈夫ですが、 '(\ f - >(f True、f 'a'))id'はエラーです。 –
@DanielWagnerなぜこれが起こりますか? 'id'は多相ではないのですか? –
はい、実際には、 'id'は多相です。 '\ f - > ...'は多態性を持つことができます。しかし、 '...'の内部では、 'f'自体は多型ではありません! '\ f - >(f True、f 'a')'は既に 'id'を言及していない型エラーです。この制限は、型推論をより簡単にし、ある型を与えることができるすべての用語が最も一般的な型を持つ望ましい特性を保持するために設けられています。 –