返回文章列表

文章

关于Clojure和ClojureScript

目录
  1. 🧩 Clojure vs ClojureScript 对比总览
  2. 🔍 关系总结
  3. 🧠 设计哲学
  4. 🧰 实践应用场景
  5. 💡 总结一句话

🧩 Clojure vs ClojureScript 对比总览#

维度ClojureClojureScript说明 / 对比分析
定位运行在 JVM 的 Lisp 方言运行在 JavaScript 平台的 Lisp 方言二者是同一语言在不同宿主平台的实现
目标平台Java 虚拟机(JVM)JavaScript 引擎(浏览器、Node.js、Deno)编译目标不同
编译产物JVM 字节码(.class 文件)JavaScript 代码(.js 文件)对应宿主环境不同
标准库调用Java 标准库JavaScript 全局对象 / DOM APIClojureScript 无法直接调用 Java 类
构建工具Leiningen、deps.edn、tools.buildshadow-cljs、figwheel、Lumo 等shadow-cljs 是最常用的 ClojureScript 构建工具
并发模型基于 JVM 的并发支持:futureagentatomref没有线程,依赖 core.async(基于 channel 的异步模型)JS 单线程,使用 CSP 异步风格
I/O 操作文件系统、Socket、HTTP(基于 JVM)浏览器 fetch、Node.js fs 等与宿主环境能力挂钩
类型系统JVM 数值类型(int, long, BigDecimal 等)JS 的 Number 类型(双精度浮点)可能存在数值精度差异
可交互环境 (REPL)基于 JVM基于 JS 引擎(浏览器 / Node)都提供 REPL 交互式开发体验
主用途服务端、数据处理、并发编程、后端系统前端开发、Web 应用、跨平台 JS 逻辑一般成对使用(Full-stack Clojure)
生态系统Java 生态(使用任何 Java 类库)JS 生态(npm 包、React、Node 模块)ClojureScript 可直接与 npm 集成
DOM 支持直接操作 DOM(通过 js interop)前端特有能力
Interop(互操作性)(import 'java.time.Instant) 可直接用 Java 类(js/Date.), (.-title js/document) 操作 JS 对象ClojureScript 用 js/ 前缀访问原生对象
示例打印(println "Hello from JVM") → 控制台输出(js/console.log "Hello from Browser") → 浏览器控制台输出输出环境不同
运行环境差异JVM 多线程、GC、类加载器等特性JS 单线程、事件循环并发与性能模型完全不同
共享代码机制可使用 cljc 文件跨平台.cljc 文件可在 Clojure 与 ClojureScript 同时编译通过 reader conditional #?(:clj ... :cljs ...) 区分平台
示例(共享代码)clojure (defn now [] #?(:clj (java.time.Instant/now) :cljs (js/Date.)))同上同一文件跨平台运行
最终定位JVM 世界的函数式语言JavaScript 世界的函数式语言同语法不同宿主,统一思维模型

🔍 关系总结#

概念描述
同语法都是 Lisp 方言,语法几乎完全一致(S-expression)
同核心语言ClojureScript 的 Reader、宏系统与 Clojure 共用大部分设计
不同标准库受宿主环境约束:Clojure 用 Java,ClojureScript 用 JS
共享生态可以使用 .cljc 文件实现逻辑共享
理念一致函数式、不可变数据、REPL 驱动开发、宏元编程

🧠 设计哲学#

ClojureScript 并不是「Clojure 的子集」,而是:

“Clojure 的另一种实现(different host, same language)” Rich Hickey在设计中希望:

  • 语言层面统一:学习一次即可写 JVM 和 JS;
  • 宿主差异隔离:库层抽象宿主特性;
  • 可移植性:核心逻辑代码可在多平台复用;
  • 宏系统一致:两边共享语法扩展能力。

🧰 实践应用场景#

场景推荐
Web 后端✅ Clojure(基于 JVM)
Web 前端✅ ClojureScript(基于 React + Reagent 或 Rum)
全栈开发✅ Clojure + ClojureScript(共享业务逻辑)
桌面 / 移动端✅ 通过 Electron + ClojureScript 或 React Native + CLJS

💡 总结一句话#

Clojure 是运行在 JVM 上的函数式 Lisp。 ClojureScript 是运行在 **JavaScript **平台上的 Clojure。 二者共享语法、哲学和思维方式,只是运行时和生态不同。