为什么这段代码有效?
(defn g []
do (println 10) (println 20))
注意:没有(在做之前。
答案 0 :(得分:8)
理论上这不应该编译。编译器应该抱怨do
无法解析,因为它是一个不在表单第一个位置的特殊符号。
对于do
特殊形式和fn*
特殊形式的正文,使用相同的BodyExpr parsing code可能会产生(可能是非预期的)后果。编译do
特殊表单时,将删除前导do
并编译其余表单。对函数体使用相同的解析器意味着单个裸do
也可以首先出现。
public static class BodyExpr implements Expr, MaybePrimitiveExpr{
...
public Expr parse(C context, Object frms) {
ISeq forms = (ISeq) frms;
if(Util.equals(RT.first(forms), DO))
forms = RT.next(forms);
....
您会注意到,如果重复do
,则
(defn g [] do do (println 10) (println 20))
;=> CompilerException java.lang.RuntimeException:
Unable to resolve symbol: do in this context ...
按预期不编译。