1

ここで何が問題なのですか?

module Main
    where

import System.IO

main = do
    hSetBuffering stdin LineBuffering
    numbers <- ask -- parse error on input `numbers'
    putStrLn "The sum of all numbers is:"
    putStrLn $ sum numbers
    putStrLn "The product of all numbers is:"
    putStrLn $ product numbers

ask :: (Read a, Eq a, Num a) => IO [a]
ask = do
    putStrLn "Enter a number to add it to the list. Enter zero to terminate the list."
    input <- getLine
    let n = read input
    if n == 0
    then return []
    else do
        rest <- ask 
        return (n : rest)
4

1 に答える 1

1

の型シグネチャを見てみましょうputStrLn:

> :t putStrLn
putStrLn :: String -> IO ()

ain にaskは明示的な型シグネチャがないため、Haskell/GHC はそれを使用するメソッドから推論します。

したがって、メソッドがあるためputStrLn a、これが可能な唯一の方法は ifa :: Stringです。

ただし、 の型シグネチャではsum:

> :t sum
sum :: (Num a) => [a] -> a

a型クラスのインスタンスでなければなりませんNum。(あなたのask関数もこれを指定しています)。

GHC はそれが ...でa なければならないことを知っていますが、 . が必要です。 は、少なくともプレリュードでは、 のインスタンスではありません。StringsumNumStringNum

ここに矛盾が現れる。

プログラムをチェックするようなプログラムを使用することをお勧めしghc-modます。より役立つエラー メッセージが表示される場合があります。これが私が得たものです:

No instance for (Num String)

これは、私たちが結論したこととよく一致しています。

この場合の解決策は、最初にあなたNumをに変えることStringです:

> :t show
show :: (Show a) => a -> String

為に:

putStrLn $ show $ sum numbers

幸いなことに、次のprintStrLn . showようにエイリアスされていprintます。

> :t print
print :: (Show a) => a -> IO ()

あなたが使用できるように

print $ sum numbers
于 2013-08-02T11:10:03.190 に答える