2024 年 Clojure 状态调查!中分享您的想法。

欢迎!请查看关于页面以获取更多关于如何使用本站的信息。

0
Clojure

在 1.4 版本和最新主分支上

user> (defn ten () 10)

'user/ten

user> (doall (pmap #(with-redefs (fn [] ten) (%)] (ten)) (range 20 100)))
(20 21 22 23 24 25 34 27 28 29 30 31 32 33 34 35 36 37 38 39 39 35 42 43 44 45 48 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 79 87 88 89 90 91 92 93 94 95 97 92 98 99)
user> (ten)
79

不确定这究竟是否是一个缺陷,但文档并未提及并发安全问题,我预期任何(任意交错)的 with-redefs 调用序列后都会恢复原始值。

5 答案

0

评论者:timmc

with-redefs 文档(v1.4.0版本)表示“这些临时更改将在所有线程中可见。”这听起来似乎不是线程安全的。

一般来说,var 根绑定修改不是线程安全的。

0

评论者:bendlas

据我所知,with-redefs 主要用于测试套件中模拟 vars。当 vars 默认变为静态时,它被引入,许多测试套件曾使用绑定进行模拟。也许应该修改文档字符串,添加类似的内容:使用此功能时,您必须确保只有一个线程与已重新定义的 vars 交互。

0
by

评论由:stu 撰写

行为检查无误,文档字符串的修改很好。

0
by

评论由:jafingerhut 撰写

2012年11月25日的补丁 clj-1104-doc-unsafety-of-concurrent-with-redefs-v1.txt 更新了 with-redefs 的文档字符串,使其更明确地说明并发使用是不安全的。

0
by
参考:[https://clojure.atlassian.net/browse/CLJ-1104](https://clojure.atlassian.net/browse/CLJ-1104)(由 jawolfe 报告)
...