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

欢迎!请参阅关于页面,了解更多关于如何使用本网站的信息。

+1
编译器

原始函数和 recur 变量无法通过 (try) 清洁地传递;它们被装箱为 Object。这会导致使用原始类型的函数或循环出现反射警告。

`
user=> (set! warn-on-reflection true)
true

user=> (fn [] (loop [t 0] (recur t)))

<user$eval676$fn677 user$eval676$fn677@3d80023a>

user=> (fn [] (loop [t 0] (recur (try t))))
NO_SOURCE_FILE:1 recur 参数 for 基本局部变量 t 不匹配原始参数,已有:Object,需:long
自动装箱循环参数:t

<user$eval680$fn681 user$eval680$fn681@5419323a>

user=> (fn [^long x] (recur (try x)))
NO_SOURCE_FILE:1 recur 参数 for 基本局部变量 x 不匹配原始参数,已有:Object,需:long

CompilerException java.lang.IllegalArgumentException: recur 参数 for 基本局部变量 x 不匹配原始参数,已有:Object,需:long,编译:(NO_SOURCE_PATH:1:1)
`

7 答案

0

评论者:davidj

不讨论最理想的行为,下面的代码不会引起反射警告

`
user=> (set! warn-on-reflection true)
true
user=> (fn [] (loop [t 0] (recur (long (try t)))))

<user$eval673$fn674 user$eval673$fn674@4e56c411>

`

0

评论者:bronsa

相关票http://dev.clojure.org/jira/browse/CLJ-701

0

评论者:hiredman

编译器中的try/catch仅实现Expr,而不是MaybePrimitiveExpr,看起来扩展TryExpr以添加MaybePrimitiveExpr非常简单,但实际上recur在语句上下文中分析其参数,导致(try ...)在本质上将自己包装成一个类似于((fn (link: ) (try ...)))的函数,这时它成为一个invokeexpr,添加MaybePrimitiveExpr变得非常困难,并且它与CLJ-701的相同案例

0

评论者:hiredman

链接http://dev.clojure.org/jira/browse/CLJ-701 尝试解决此问题

0

评论者:alexmiller

我应该将其克隆到CLJ-701吗?

0

评论者:hiredman

如果您想要try从返回上下文中的修复成为CLJ-701的一部分,那么它就是重复的,如果您不确定或者更希望701保持更集中的(我的补丁可能不可接受,或者可能太大,做了太多)那么它不是重复的。我有点自作主张地解决了CLJ-701上的补丁中的两个问题,因为我是通过Nicola在此处的评论来到CLJ-701的,并且相同的编译器机制可以用于两者。

我认为状态取决于CLJ-701的状态。

0
...