评论文由:cgrand撰写
这里的建议是捕获递归序列实现(即当计算懒序列的体时尝试访问同一个序列)并抛出异常。
目前,当这种情况发生时,递归访问序列返回nil。这导致看似正常但产生错误结果或出于偶然产生正确结果的代码(见https://groups.google.com/d/topic/clojure/yD941fIxhyE/discussion中的示例)。
因此,这个补丁在所有可能递归的方法调用之前(.seq中的.sval和.sval中的.invoke)对LazySeq状态(f,sv和s字段)的修改进行调整,以确保重入时LazySeq的状态是一致的,并能传达seq已经开始计算的事实。
目前递归调用可能会发现f和sv被清除,并得出计算已完成且结果在s中的结论,尽管s还没有受到影响。
目前
|状态|f|sv|s|
| :-- | :-- | :-- | :-- | :-- |
|未实现|非空|null|null|
|已实现|null|null|任何内容|
|正在实现/从fn.invoke发起的递归调用|null|null|null|
|正在实现/从ls.sval发起的递归调用|null|null|null|
请注意,“正在实现”状态与未实现或已实现重叠。
(注:“任何内容”包括null)
有了这个补丁
|状态|f|sv|s|
| :-- | :-- | :-- | :-- | :-- |
|未实现|非空|null|null|
|已实现|null|null|除这个以外的任何内容|
|正在实现|null|null|这个|