Haskell IO环境下使用mapM函数打印键值元组列表的问题
问题原因
你对print和mapM的功能理解没有错误:
print可以将任意实现了Show类型类的值输出到终端,类型为Show a => a -> IO ()mapM可以遍历列表,对每个元素执行传入的一元操作,类型为Monad m => (a -> m b) -> [a] -> m [b]
报错的核心原因是类型不匹配:mapM print finalList执行后的返回值类型是IO [()](会收集所有print调用的返回值()组成列表),但main函数要求必须返回IO ()类型,因此触发类型错误。
解决方法
方法1:使用mapM_替代mapM(最推荐)
Haskell标准库中以下划线结尾的遍历函数,都会直接忽略操作的返回值,mapM_ print finalList的返回类型刚好是IO (),完全符合main的类型要求,代码示例:
main = do let finalList = mergeKey x mapM_ print finalList
执行后会逐行打印列表中的每个键值对:
("Hi",1) ("Hello",5)
方法2:直接打印整个列表
如果不需要逐行输出,列表本身已经实现了Show类型类,直接调用print finalList即可一次性打印完整的列表内容,不需要额外遍历:
main = do let finalList = mergeKey x print finalList
执行后输出:
[("Hi",1),("Hello",5)]
方法3:手动忽略mapM的返回值
如果你一定要使用mapM,可以用void函数丢弃返回的[()],让返回类型符合要求:
import Control.Monad (void) main = do let finalList = mergeKey x void $ mapM print finalList
该写法和mapM_效果完全一致,但冗余度更高,没有特殊需求不推荐使用。
内容的提问来源于stack exchange,提问作者Niki
相关产品推荐
相关产品推荐

