You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何改写Clojure宏使其输出原始代码并正确显示序列结果?

解决方案

针对你的两个问题,我们可以通过以下方式修改宏:

核心修改点

  1. 保留原始代码结构:原宏使用'~form会在宏展开时求值form并quote结果,导致代码被展开。改为在宏展开阶段用pr-str直接获取form的结构字符串,避免不必要的展开。
  2. 正确显示序列结果:原宏直接用str转换结果,lazy seq这类对象会输出内存地址。改为用pr-str序列化结果,确保集合、序列以可读形式展示。
  3. 移除冗余函数:原symbol-several函数将字符串拼接为symbol无实际意义,改为直接输出内容。

修改后的代码

(defn clean-code-str
  "移除代码字符串中的clojure.core命名空间前缀,贴近手写形式"
  [s]
  (clojure.string/replace s #"clojure\.core/" ""))

(defmacro ! [& forms]
  `(do
     ~@(for [form forms]
         `(let [result# ~form]
            (println (str ~(clean-code-str (pr-str form)) " ;-> " (pr-str result#)))
            result#))))

效果验证

  • 执行(! (map inc [1 2 3])),输出:
    (map inc [1 2 3]) ;-> (2 3 4)
    
  • 执行(! (do (def v [3 4]) (def l '(1 2)) (0 ~@l ~@v)))`,输出:
    (do (def v [3 4]) (def l '(1 2)) (seq (concat (list '0) l v))) ;-> (0 1 2 3 4)
    

注:由于Clojure reader会提前解析反引号(`)和unquote(~)语法,宏无法完全还原原始输入的反引号写法,但已避免将unquote的结果直接展开为具体值,保留了代码的结构逻辑。

内容的提问来源于stack exchange,提问作者Nikolay Kudinov

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.10 15:50:20