如何在Haskell中过滤无限列表 [英] How to filter an infinite list in Haskell
问题描述
可能重复:
对无限列表的有限理解
Possible Duplicate:
Finite comprehension of an infinite list
我不明白为什么ghci无法正确计算此代码?
I can't understand why ghci can't compute this code correctly?
[x | x <- [1..], x < 1000]
GHCI刚好停在最后一个数字,我需要在命令行中中断此过程以恢复到正常状态.怎么了?我希望由于haskell的懒惰评估,该代码应该能正常工作.
Ghci just stops at last number and I need to interrupt this process in command line to get back to normal state. What's wrong? I expect that this code should work because of haskell's lazy evaluation.
推荐答案
[x | x <- [1..], x < 1000]
等同于filter (< 1000) [1..]
;您要改为takeWhile (< 1000) [1..]
.
那么filter
和takeWhile
有什么区别?
好吧,如果您尝试评估整个结果---这就是ghci所做的,以便打印出来---那么filter
将测试输入列表中的每个元素,以确定是否应该在输出列表中.后第一个千元?它进行测试. filter
不知道它不会突然遇到..., 12345, 12346, -7, 12348, ...
.
Well, if you try to evaluate the entire result --- and that's what ghci does, in order to print it --- then filter
will test each and every element in the input list to determine whether it should be in the output list. After the first thousand elements? It carries on testing. filter
doesn't know that it isn't suddenly going to encounter ..., 12345, 12346, -7, 12348, ...
.
另一种查看方式是filter
到达输入列表的末尾时只能说输出列表在这里结束".如果为它提供无限列表,则永远无法确定它已生成输出列表的所有元素.因此它将似乎挂起.
Another way of looking at it is that filter
can only say "the output list ends here" once it's reached the end of the input list. If you feed it an infinite list, it can never be sure it has generated all elements of the output list. So it will appear to hang.
takeWhile
一旦到达条件失败的元素,就会停止并终止其输出列表.
takeWhile
, on the other hand, stops and terminates its output list as soon as it reaches an element that fails the condition.
这篇关于如何在Haskell中过滤无限列表的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!