请在2024年Clojure调查中分享您的想法!

欢迎!请参阅关于页面以获取更多关于此如何工作的信息。

+1点赞
Clojure

如果merge使用transients会更好。

补丁
- clj-1458-7.patch

方法
将c.c/merge迁移到核心代码库中,在transients和reduce之后。保留旧版本merge1以便在涉及较新定义之前的情况中使用。使APersistentMap/conj和ATransitionMap/cons意识到IKVReduce。

附带的补丁保留了merge的两种现有行为
- 元数据传播
- 合并的右侧可以是Map.Entry,一个size=2的IPersistentVector以及常规映射。

经请求筛选

25 个答案

0点赞

评论由:jawolfe发表

我今天将尝试一下补丁。

0点赞

评论由:jawolfe发表

这个补丁(transient-merge.diff)使得merge、merge-with,以及zipmap(因为它紧挨着,并且显然也可以从transients中受益)使用transients。

三个潜在问题
- 由于这些函数依赖于transient和相关函数,我不得不移动它们。我假设这比正向声明更好。这是我找到的最佳位置,但我愿意将它们移动到其他地方。
- 为了避免将单个参数transient化可能带来的性能成本,我添加了多个参数。如果需要,我愿意撤销这一举措。
- 由于transient映射不支持contains?(或find),我不得不稍微修改merge-with中的逻辑。

0点赞

评论者:michalmarczyk

我于2012年5月30日为{{zipmap}}创建了一个单独的工单,包括补丁,工单编号:CLJ-1005。

0点赞

评论由:jawolfe发表

哎呀,如果我当时越界的话,很抱歉。如果这样能简化问题,我愿意从这次的补丁中移除那个变化——只需告诉我。

0点赞

评论者:gshayban

附件中提供了另一种方法,即在协议加载后延迟合并,然后使用transducers。

0点赞

评论者:michaelblume

看起来你在获取 m k 时做了两次——这不应该被放在局部变量中吗?

0点赞

评论者:michaelblume

嗯,我在局部变量中说的“put”是不当的,‘throw’这个词的选择是错误的。

0点赞

评论者:gshayban

是的,那是对的——在 CLJ-700 提交后,将不会使用 get。

我们应该添加性能测试。合并两个、三个、很多个映射,以及不同大小的映射;对于 merge-with,改变碰撞率。

需要回到(某些标识符)逻辑,否则元数据会从除第一个提供的映射之外的其他映射中传播。我稍后再修复。

0点赞

评论者:michaelblume

我不知道这是否应该被允许,但是这会破坏

(merge {} (link: :foo 'bar))

这在 compojure-api 中广泛使用。

0点赞
0点赞

评论者:michaelblume

Ghadi,contains? 在底层使用 get,所以它仍然是两次获取,对吗?看起来坚持使用 ::none 技巧会更有性能。

0点赞

评论者:bronsa

这需要 if-let + find。

0点赞

评论者:gshayban

新的补丁解决了一些现有的担忧

0点赞

评论者:gshayban

CLJ-1458-transient-merge3.patch 移除愚蠢的内联宏,使用单例函数。

0点赞

评论者:michaelblume

不错 =)

这应该附带测试。如果我们想保留合并到 MapEntry 的能力,我们应该对其进行测试。这与其说是补丁的弱点,不如说是现有测试的弱点。我在测试套件中看到了 merge 和 merge-with 几次使用,但我没有看到旨在测试它们行为的测试。

...