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

欢迎!请参见关于页面以了解如何工作的更多信息。

+5
Clojure

虽然没有assoc-in,但确实有clojure.core/dissoc-in。
确实,可以使用update-in和dissoc构建dissoc-in,但这也是对assoc-in的反对。
当提供assoc-in的快捷方式时,也应该有一致的dissoc-in快捷方式。
实现类似于assoc-in。

16 个回答

+1

评论者:alexmiller

我们必须考虑除了地图之外的其他向量或关联数据结构。我也不想设置标志,而是留为可变参数以删除多个。

使用等效于

(update-in [{:foo 1}] [0] dissoc :foo)

我们最终会留下{{[{}()]}},所以现有的这种方法确实会留下空集合。

我还查阅了一些现有的dissoc-in实现——如core.incubator,taoensso.encore,clj-http,medley,useful,plumbing等。大部分使用单个键路径并且留下空集合——这些似乎大多源自incubator版本。Encore使用多个路径,通过将键路径与最终要删除叶键分开来实现(可变参数)。Medley、useful和plumbing只针对map,并删除空map。

我想象不出我们会把这个在核心中写成专门针对map的版本(因为其他-in函数都是通用的),所以我得出结论,我们需要一个允许留下空集合的dissoc-in。鉴于这一点,我不确定dissoc-in是否比update-in + dissoc提供了足够的价值,值得在此时添加到核心中,特别是鉴于它存在于各种实用库中(在很多情况下具有不同的语义)。这样我们可能会破坏(或至少让)现有dissoc-in实现的用户感到不便。我将对此保持开放态度,但此时我倾向于拒绝这个增强功能。

+1

评论者:alexmiller

是的,尽管我认为在更新案例中,这些因素平衡方式有所不同。在更新中,实现更少,并且它们与我们计划添加的内容相匹配。因此,它们为用核心功能替换现有内容创造了潜力。

我认为常见的实用库实现(flatland/useful/plumbing)实际上满足的是不同的需求——仅在maps上执行update-in、dissoc和路径删除。因此,如果目标是要涵盖常见的用法,那么我们需要确保它只在maps上工作,并删除留下的空路径。然而,我认为这与其他核心-in函数有点不一致。我认为也许可以在路径删除的同时,使其适用于除了maps以外的对象,这样可以满足实用库所指示的需求,并且像其他-in函数一样通用。如果您需要留下空集合,您可以像现在一样执行 update-in+dissoc。

0

评论者:jafingerhut

2012年9月13日的补丁 clj-1063-add-dissoc-in-patch-v2.txt 替代了2012年9月7日的 001-dissoc-in.diff。它修复了一个错误(文档字符串缺失最后的“),并添加了新函数的测试用例。

0

评论者:bronsa

感谢修复 Andy

0

评论者:jafingerhut

这个提议的dissoc-in应该与clojure.core.incubator中的dissoc-in进行比较,我偶然发现它。我发现它们的格式不同,但还没有检查它们是否有行为上的差异。

https://github.com/clojure/core.incubator/blob/master/src/main/clojure/clojure/core/incubator.clj

0
_评论者:bronsa_

clojure.core.incubator中的dissoc-in递归删除空maps

user=> (clojure.core.incubator/dissoc-in {:a {:b {:c 1}}} [:a :b :c])
{}

而本补丁中的one在预期情况下不做(display)

user=> (dissoc-in {:a {:b {:c 1}}} [:a :b :c])
{:a {:b {}}}
0

stu 做出的评论:

请在孵化器中完成这项工作。

0

andrewhr 做出的评论:

保留空路径是否真的是最期望的行为?我认为,由于 {{assoc-in}}/{{update-in}} 在过程中创建了路径,这种行为看起来就像是真正的“双重”。

当遇到 {{nil}} 幻像时,可能发生哪些不良情况?这些问题对 {{dissoc-in}} 用户来说是否太过模糊?

0

评论者:alexmiller

补丁中的测试过于简单。应该测试多层、记录、矢量等。

0
_ [email protected] 做出的评论:

正在测试 "clj-1063-add-dissoc-in-patch-v2.txt"。


(dissoc-in {} [:a :b :c])
=> {:a {:b nil}}


这种行为相当出乎意料。尽管孵化器版本没有这个问题,但它确实删除了空映射。

我正在为此补丁编写测试(也可能是新的 dissoc-in),但对我来说,是否保留空路径还不清楚?我不介意两种方式,尽管我倾向于同意 Andrew Rosa 的意见,即保留它们更为对称。
0

[email protected] 做出的评论:

@alex,你希望保留空路径还是删除它们?两种方式都是可以接受的,尽管总的来说,我略微倾向于保留它们。一旦我知道你想走哪条路,我可以为这个方向编写测试。

0

评论者:alexmiller

一个选择与另一个选择之间的权衡是什么?

在人们使用 dissoc-in 代理(update-in 与 dissoc 等结合)的地方,他们期望的行为是什么?

0
评论者:michalmarczyk

如果我们只想处理嵌套在映射中的映射……,我可能更倾向于移除空子路径。

然而,如果我们想在这个过程中接受向量,那么保留空路径在该情况下会产生清晰的语义


(dissoc-in [{:foo 1}] [0 :foo])
;= [{}]


相比之下,删除空路径似乎会导致需要解决的问题,这些问题必须通过限制移除路径的行为仅限于映射或当向量中的子路径变成条目时抛出异常来解决。这两种方法似乎都不太理想。
0

评论者:michalmarczyk

我们还可以在技术上接受一个标志来决定是否应该删除空路径,并让用户确保只在没有向量的情况下传递 {{true}}。然而,我并不是很喜欢这种方法,因为它似乎表明额外的参数的更自然目的是提供额外的路径以供 dissoc 自由变量匹配 {{dissoc}} 和 {{dissoc-in}} 语义(参看 CLJ-1771)。

0

评论者:bronsa

同样的论点也可以用于包含 update。实际上,updatedissoc-in 都可以在几个实用库中找到,这应该表明人们并不满足于仅仅使用 update-in + dissoc

当然,将其添加到核心会导致在使用某些库时发出警告(它不会破坏任何事情,因为导致 update 出现破坏的 AOT 错误已经修复了)但是我认为这并不是一个大问题;那些库的新版本将很快发布,即使不是这样,警告也不是世界的末日。

...