2012-01-12 15 views
3

バックストーリー:私は先週、Learn You A Haskellを読んで先週、この問題に苦労していましたが、私はそれを理解できません。ハスケルでリストに文字列を分割する

私はリストの理解と再帰を理解することで多くの進歩を遂げましたが、この1つの問題はまだ私の方法で立っている一つの問題です。

質問:私はString(または私がStringと考えるもの)を分割リストに変換しようとしています。ここに私がこれまで持っていたコードがあります。 .txtファイルの内容をインポートします。

import System.Environment 

main :: IO() 
main = do 
    args <- getArgs 
    if null args 
     then putStrLn "usage: ./pattern dataset.txt" 
     else do contents <- readFile $ head args 
       putStrLn $ "Filer1: " ++ filterLower(contents) 
       convert' contents 

filterLower :: String -> String 
filterLower st = [ c | c <- st, c `elem` ['A'..'Z']] 

私は自分のCONVERT関数を作ってみました:それは作品

convert' :: String -> [String] 
convert' x = (x:[]) 

が、それはこの問題のために動作しません。

ご協力いただければ幸いです。

エラー:これは私が定期的に受けるエラーです。

Couldn't match expected type `IO()' with actual type `[String]' 
    In the return type of a call of `convert'' 
    In the expression: convert' contents 
    In the expression: 
     do { contents <- readFile $ head args; 
      putStrLn $ "-: " ++ filterLower contents; 
      convert' contents } 
+3

あなたが遭遇したエラー/問題は何ですか? –

+0

私はちょうど私のエラーを投稿に追加しました。 –

+0

あなたは 'convert''を呼び出した後に何が起こると思いますか?結果を投げ捨てようとしているように見えます。あなたはそれを印刷しようとしません。 – dave4420

答えて

6

問題はconvert'の結果は、文字列のリストですが、IOアクションとしてそれを使用しようとしているということです。あなたは結果で何かをしなければなりません。たとえば、

print $ convert' contents 

のような結果が画面に表示されます。または、たとえばmapM_ putStrLn各要素を独自の行に出力します。それともあなたはそれに名前を付け、など、文を書き続けることができる:

let converted = convert' contents 
... 

あなたのコメントで行く、あなたが、文字列を分割しようとしている方法は、その単語のリストにそれを回すためにあるようです、例えば convert' "Hello world"["Hello", "world"]。その場合、 convert'はまったく必要ありません。標準 wordsの機能はそれだけです!したがって、 words contentsを使用し、 convert'を定義することはできません。

+0

1月は単語について私に語っていることを覚えていますが、それが機能であることはわかりませんでした。しかし、私は今までにハスケルのすべてが機能だと知っていたはずです。 :D私は今トラックに戻ります。ご協力ありがとうございました。 –

+2

@SubtleArray、FWIW、ハスケルのすべてが関数であるということは真実ではありません。例えば、文字列 '' thisは関数ではありません ""は真実です。関数のみが;-) – luqui

+0

http://conal.net/blog/posts/everything-is-a-function-in-haskell –

5

convert' :: String -> [String]ですので、convert' contents :: [String]は単なる文字列のリストです。しかし、あなたは、IO-ブロックに

タイプ IO somethingの表現だけを表示することができ
do contents <- readFile whatever 
    putStrLn $ ... 
    convert' contents 

それを置いてきました。 IOブツにIO-以下の式を作成する簡単な方法は、それだけでreturn、あります:

do contents <- readFile ... 
    putStrLn $ ... 
    return $ convert' contents 

が正しく入力されています。しかし、このdo-blockはタイプIO [String]なので、宣言されたタイプmainと一致しません。どのように修正するかは、プログラムで何をしたいかによって異なります。

+0

私は参照してください。これは、C++関数のようなもので、その型によって機能が制限されています。説明をありがとうございます。私はHaskellにはまったく新しいです、そして、私はまだ構文を回避しようとしています。 –

1

ここで何をしようとしているのか分かりませんが、最大の問題はdoブロックを正しく使用していないことです。いくつかのa用タイプIO aを持っている必要がありますdoブロックで(<-なし声明)

  • ごとに「裸」の文:mainは、2つの制約を意味IO()を、入力しています。
  • doブロックの最後の文は、タイプIO()でなければなりません。最終的なステートメントのタイプは[String]です(したがって、エラーが発生しています)。そのタイプの最も単純なステートメントはreturn()です。