[英]Haskell IO create a list of strings and display it
我正在嘗試編寫一個程序,允許用戶通過一次輸入一個字符串來建立字符串列表,並在每個步驟后顯示列表。
到目前為止,這是我的代碼:
buildList :: [String] -> IO ()
buildList arr = do
putStr "Enter a line:"
str <- getLine
if str == "" then
return ()
else do
let newarr = arr : str
putStrLn ("List is now: " ++ newarr)
buildList newarr
listBuilder :: IO ()
listBuilder = do
buildList []
listBuilder
通過傳入空列表來啟動列表,我正在嘗試使用遞歸,以便代碼一直運行,直到用戶輸入空字符串。
它沒有用,歡迎任何想法
這是一個理想的輸入:
Enter a line: hello
List is now ["hello"]
Enter a line: world
List is now ["hello","world"]
Enter a line:
錯誤:
Couldn't match type `Char' with `[String]'
Expected type: [[String]]
Actual type: String
In the second argument of `(:)', namely `str'
In the expression: arr : str
In an equation for `newarr': newarr = arr : str
編輯:
由於線索和使用show
,這修復了它
buildList :: [String] -> IO ()
buildList arr = do
putStr "Enter a line:"
str <- getLine
if str == "" then
return ()
else do
let newarr = arr++[str]
putStrLn ("List is now: " ++ show newarr)
buildList newarr
listBuilder :: IO ()
listBuilder = do
buildList []
你可以通過這個工作
(a)使用arr++[str]
而不是arr:str
將新字符串放在列表的末尾,因為:
只能像singleThing:list
一樣使用,
(b)將跑動分為單獨的功能,和
(c)將結果傳遞給return
以便您可以在程序的其他地方使用它
buildList arr = do
putStrLn "Enter a line:"
str <- getLine
if str == "" then
return arr
else do
tell (arr++[str])
tell arr = do
putStrLn ("List is now: " ++ show arr) -- show arr to make it a String
buildList arr
給
Enter a line:
Hello
List is now: ["Hello"]
Enter a line:
world
List is now: ["Hello","world"]
Enter a line:
done
您可以使用pipes
和foldl
庫以聲明方式解決此問題:
import Control.Foldl (purely, list)
import Pipes
import qualified Pipes.Prelude as P
main = runEffect $ P.stdinLn >-> purely P.scan list >-> P.print
您可以將其讀作管道:
P.stdinLn
是用戶輸入的行的源
P.scan
行為類似於Data.List.scanl
,管道而不是列表除外。 purely P.scan list
表示要連續輸出到目前為止看到的值。
P.print
這些輸出列表打印到控制台
以下是此管道的實例示例:
$ ./example
[]
Test<Enter>
["Test"]
ABC<Enter>
["Test","ABC"]
42<Enter>
["Test","ABC","42"]
<Ctrl-D>
$
您也可以通過將參數更改為purely scan
來輕松切換折疊線的其他方法。 例如,如果使用Control.Foldl.vector
切換list
,則它將輸出行而不是列表的向量。
問題是:
data構造函數只能用於將元素追加到列表的開頭。 當您編寫let arr=arr:str
,您正在使用它將元素放在列表的末尾。 相反,你可以向后構造你的列表,像這樣let arr=str:arr
或使用++
運算符將它附加到列表的末尾,就像這樣let arr=arr++[str]
。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.