[英]Mapping with IO actions in Haskell
我有一個函數,需要兩個文件名,並將這兩個文件的內容讀入String
,然后返回是否匹配。 功能如下:
f :: String -> String -> IO Bool
f fileName1 fileName2 = do
str1 <- readFile fileName1
str2 <- readFile fileName2
return (str1 == str2)
如果我從main
內部這樣使用它:
main = do
res <- f "A.txt" "B.txt"
print res
它可以工作並打印True
或False
。 我要做的是將此函數f
應用於文件名列表(元組)。 對於類似:
[("a.txt", "b.txt"), ("c.txt", "d.txt")]
(假設a.txt
和b.txt
具有相同的內容,而c.txt
和d.txt
不同)。
我想將其(文件名列表)轉換為Bool
列表,例如: [True, False]
。 我嘗試使用mapM
,但是似乎沒有映射任何內容(當我使用mapM
后打印列表時,它會打印相同的元組列表)。
所以我的問題是:我在做錯什么,如何獲得上述Bool
的列表?
請對我輕松一點,因為我對Haskell和函數式編程還很陌生:)
這是函數f'
,它可以完成您描述的操作。
f' :: [(String,String)] -> IO [Bool]
f' = mapM $ uncurry f
讓我知道不清楚的地方! 而且,為了清楚起見,這是如何運行它:
main = do
res <- f' [("a.txt", "b.txt"), ("c.txt", "d.txt")]
print res
該函數采用無點形式,因此等效於f' lst = mapM (uncurry f) lst
。 mapM
本質上使用f
作為函數映射lst
每個元素,並將IO
推送到列表的外部。
uncurry
只是采用uncurry
a -> b -> c
形式的函數,並將其轉換為一個(a,b) -> c
,這是我們想要的,因為您有一個元組列表。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.