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

欢迎!有关此机制更多信息的请参阅关于页面。

+2
core.async
  • 每次deref都会从通道中取一个值
  • 从已关闭的通道中进行deref返回nil
  • 带有超时的deref必须超时或从通道中获取值(不能两者兼得!)。可能只需要通过var调用alt!!的某个变体。
  • 高效地使用内部机制
  • 不要实现IPending/realized,这两种解释都不太理想

补丁:async-102-2.patch

deref和timed deref的实现(链接:http://dev.clojure.org/jira/browse/ASYNC-102?focusedCommentId=37211&page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#comment-37211 文本:概念上简单),但由于循环命名空间依赖关系难以实现。欢迎提出建议。

8 答案

0
_由:stu_发表评论

async-102.patch与描述“通道已关闭时变为realized”不匹配——相反,当有值可用时通道变为realized。 这两种解释对我来说都似乎有问题,我认为需要澄清{{realized?}}的定义来支持这种新情况。  Clojure中{{realized?}}的其他用法都保证后续的deref将会立即填充,但如果另一个消费者取走值,通道将不会是这样。

解决这个问题后,在筛选之前我需要为core.async实现协议提供更好的文档字符串。 对线程使用有什么保证? 工作在哪里排队,如果队列已满会发生什么?
0

由:alexmiller发表评论

我实现的`realized?`基于Rich对你问题的回答(来自内部聊天):“开启+空= false,否则为true”,我坚信这应该已经实现并反映在测试中。这也比我仅在关闭时实现更有意义。

你的评论与`realized?`的其他情况似乎准确,所以我同意这是个问题。

你能更具体地说明是哪种实现协议吗?我猜你具体指的是通道和缓冲区。任何线程都可能调用到通道。M2MC使用互斥锁保护其内部状态,并将调用的请求转发到缓冲区。所有对缓冲区的调用都受到通道互斥锁的保护。M2MC在`puts`和`take`列表中排队等待的`puts`和`take`操作,它们的数量被固定的大小限制`clojure.core.async.impl.protocols/MAX-QUEUE-SIZE`(1024)所限制,此时会抛出异常。

0

由:alexmiller发表评论

在ManyToManyChannel上使用现有的异步构建实现IDeref和IBlockingDeref的概念实施方案相对简单

`
(deftype ManyToManyChannel
#_现有代码...
IDeref
(deref [this] (<!! this))

IBlockingDeref
(deref [this ms timeoutValue]

(alt!!
  this ([val _] val)
  (timeout ms) timeoutValue)))

`

然而,M2MC在`clojure.core.async.impl.channels`中定义,`

`
(def ^:private <!!' (delay (find-var 'clojure.core.async/<!!)))

;; 然后
IDeref
(deref [this] (@<!!' this))
`

然而,对于等效的`alt!!`,它是一个围绕`do-alt`和`alts`的宏,我有一点困惑。

0

评论者: gshayban

不要依赖于解决循环依赖。相反,创建一个共享的`alt-flag`并将两个处理器入队(链接:1)。fret将提供承诺,然后 deref承诺。

(链接:1) https://github.com/clojure/core.async/blob/master/src/main/clojure/clojure/core/async.clj#L230-L231

0

由:alexmiller发表评论

新的补丁回到之前的阻塞deref实现(基本上是`

0

评论者:fogus

不过,我在如何使用
alt!!做到等效的方法上有些困扰,它是围绕do-alt和alts!!的一个宏。

我想知道以下方法是否可以解决alts!!的问题

(def ^:private ^:macro alts!!' (deref (find-var 'clojure.core.async/alts!!)))

然后在IBlockingDeref的deref实现中使用它。就目前情况来看,由于它使用了一些core.async的具体实现细节(实际上和相同),编写这段代码有些难以理解。而您实现IBlockingDeref.deref的方法则非常清晰,由于循环依赖促成的实现相对来说就不那么清晰了。虽然我不愿过多重复这一点(我似乎总是在重复),但alts!!是解决这个问题的一个清晰实现,但使用内部结构却使问题复杂化。如果可以的话,我更希望看到代码的清晰性。

话说回来,作为一个人类宏展开器,我最终还是理解了这个实现。

0

由:alexmiller发表评论

这似乎不起作用。如果你有其他成功的方案,那将非常棒!

0
参考:[https://clojure.atlassian.net/browse/ASYNC-102](https://clojure.atlassian.net/browse/ASYNC-102)( stu 提交)
...