2016-01-11 22 views
1

我寫了一個基本的遞歸函數:哈斯克爾+輸出字符串爲String類型

bibliography_rec :: [(String, String, Int)] -> String 
bibliography_rec [] = "" 
bibliography_rec (x:xs) = (citeBook x) ++ "\n" ++ (bibliography_rec xs) 

citeBook簡單地重新格式化元組爲一個字符串。

當此輸入運行:

ghci> bibliography_rec [("Herman Melville", "Moby Dick", 1851),("Georgy Poo", "Alex Janakos", 1666)] 

它產生:

"Moby Dick (Herman Melville, 1851)\nAlex Janakos (Georgy Poo, 1666)\n" 

我需要逐行打印,所以我用這個:

bibliography_rec (x:xs) = putStr ((citeBook x) ++ "\n" ++ (bibliography_rec xs)) 

我的問題是我的輸出需要的類型String不是IO()

我一直堅持這個太長,所以任何幫助都很棒!

+3

'String' *類型的值不能*產生輸出。所以你的要求(「我必須產生輸出」和「返回類型必須是字符串」)是衝突的。 –

回答

5

看起來你已經在那裏了,你只需要putStrLn這個字符串而不是print就可以了(這是默認的ghci)。 print首先通過show運行其參數,因此它會引用轉義字符,如"\n"

ghci> putStrLn $ bibliography_rec [...] 
+0

唯一的問題是我需要生成只有ghci> bibliography_rec [(...),(...)]的字符串,或者是有東西仍然缺少。還有什麼$做? – ajanakos

+0

@ajanakos絕對有你缺少的東西。一個'String'值只是一個'String'值,在Haskell中意味着它沒有副作用,並且根本無法像在屏幕上打印一樣的值。在GHCi中,當您評估一個值時,它會在幕後執行一個「IO」動作,這樣您就可以看到該值的_representation_,因爲否則GHCi的「交互」部分將不會有用。請注意,輸入GHCi的代碼與執行'.hs'文件不同。 – bheklilr

+0

@ajanakos'$'運算符有很多很多的討論,澄清等等,所有這些都是在stackoverflow和互聯網的其餘部分,我不會在這裏詳細討論,但可以說這是一個沒有操作符的操作符操作順序,以便經常放棄括號。上面的代碼行可以等效地寫成'putStrLn(bibliography_rec [...])',它在執行過程中會一樣的。這適用於'f $ g $ h 1'而不是'f(g(h 1)))',其中parens大多隻是增加噪音。 – bheklilr