質問

文字列のリストがあり、これを試しました:

ls = [ "banana", "mango", "orange" ]

main = do
       map PutStrLn list_of_strings

それはうまくいきませんでしたが、その理由がわかりません。

ghc print-list.hs
print-list.hs:3:0:
    Couldn't match expected type `IO t' against inferred type `[IO ()]'
    In the expression: main
    When checking the type of the function `main'

ヒントはありますか?これはマップが値ではなくリストを返すことに関係していると思いますが、これを修正する簡単な方法は見つかりませんでした。

現時点で私が知っている文字列のリストを出力する唯一の方法は、リストを反復して各要素を出力する関数を書くことです (リストが [a] の場合は出力しますが、(a:b) の場合は出力して再帰します)。しかし、それはそうだろう 多くの マップを使用するだけの方が簡単です...

ありがとう!

役に立ちましたか?

解決

の種類 main 関数はこうあるべきです IO t (どこ t は型変数です)。の種類 map putStrLn ls[IO ()]. 。これが、このエラー メッセージが表示される理由です。これを自分で確認するには、次のコマンドを実行します。 ghci:

Prelude> :type map putStrLn ls
map putStrLn ls :: [IO ()]

問題に対する 1 つの解決策は、 mapM, 、これはの「モナディック」バージョンです map. 。または、使用できます mapM_ それは同じです mapM ただし、関数からの戻り値は収集しません。戻り値は気にしないので、 putStrLn, を使用する方が適切です。 mapM_ ここ。 mapM_ には次のタイプがあります。

mapM_ :: Monad m => (a -> m b) -> [a] -> m ()

使用方法は次のとおりです。

ls = [ "banana", "mango", "orange" ]
main = mapM_ putStrLn ls

他のヒント

アイマンの答えは、このような状況のための最も理にかなっています。あなたは[m ()]を持っていて、m ()をしたい場合は一般的に、そしてsequence_mを含む任意のモナドできIOを使用します。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top