|
| 1 | +^{:kindly/hide-code true |
| 2 | + :clay {:title "Emmy, the Algebra System: YAMLScript for the world!" |
| 3 | + :quarto {:author :kloimhardt |
| 4 | + :type :post |
| 5 | + :date "2025-09-10" |
| 6 | + :image "sicm_ch01.png" |
| 7 | + :category :libs |
| 8 | + :tags [:emmy :physics]}}} |
| 9 | + |
| 10 | +(ns mentat-collective.emmy.fdg-ch01-ys |
| 11 | + (:refer-clojure :exclude [+ - * / zero? compare divide numerator denominator |
| 12 | + time infinite? abs ref partial =]) |
| 13 | + (:require [emmy.env :refer :all] |
| 14 | + [yamlscript.compiler :as ys] |
| 15 | + [scicloj.kindly.v4.api :as kindly] |
| 16 | + [scicloj.kindly.v4.kind :as kind])) |
| 17 | + |
| 18 | +^:kindly/hide-code |
| 19 | +(def +++ identity) |
| 20 | + |
| 21 | +^:kindly/hide-code |
| 22 | +(def mul+ *) |
| 23 | + |
| 24 | +^:kindly/hide-code |
| 25 | +(def add+ +) |
| 26 | + |
| 27 | +^:kindly/hide-code |
| 28 | +(defn ysc [s] |
| 29 | + (ys/compile (str "!ys-0\n" s))) |
| 30 | + |
| 31 | +^:kindly/hide-code |
| 32 | +(defmacro ys [s] |
| 33 | + (list 'kindly/hide-code |
| 34 | + [(list 'kind/code s) |
| 35 | + (read-string (ysc s))])) |
| 36 | + |
| 37 | +^:kindly/hide-code |
| 38 | +(kind/hiccup |
| 39 | + [:div |
| 40 | + [:script {:src "https://cdn.jsdelivr.net/npm/scittle-kitchen/dist/scittle.js"}] |
| 41 | + [:script {:src "https://cdn.jsdelivr.net/npm/scittle-kitchen/dist/scittle.emmy.js"}] |
| 42 | + [:script {:src "https://cdn.jsdelivr.net/npm/scittle-kitchen/dist/scittle.cljs-ajax.js"}] |
| 43 | + [:script {:src "https://cdn.jsdelivr.net/npm/react@18/umd/react.production.min.js", :crossorigin ""}] |
| 44 | + [:script {:src "https://cdn.jsdelivr.net/npm/react-dom@18/umd/react-dom.production.min.js", :crossorigin ""}] |
| 45 | + [:script {:src "https://cdn.jsdelivr.net/npm/scittle-kitchen/dist/scittle.reagent.js"}] |
| 46 | + [:script {:type "application/x-scittle" :src "scheme.cljc"}]]) |
| 47 | + |
| 48 | + |
| 49 | +^:kindly/hide-code |
| 50 | +(kind/scittle |
| 51 | + '(require '[emmy.env :as e :refer :all :exclude [D F->C]])) |
| 52 | + |
| 53 | +^:kindly/hide-code |
| 54 | +(def time first) |
| 55 | + |
| 56 | +^:kindly/hide-code |
| 57 | +(kind/scittle |
| 58 | + '(def time first)) |
| 59 | + |
| 60 | +^:kindly/hide-code |
| 61 | +(kind/scittle |
| 62 | + '(def D partial)) |
| 63 | + |
| 64 | +;; The Clojure code below is taken from the examples of [this previous post](https://clojurecivitas.github.io/mentat_collective/emmy/fdg_ch01.html). It is not necessary to understand what the Clojure code does, the purpose is comparison to the infix notation. |
| 65 | + |
| 66 | +(kind/scittle |
| 67 | + '(defn Lfree [mass] |
| 68 | + (fn [[_ _ v]] (* 1/2 mass (square v))))) |
| 69 | + |
| 70 | +;; The following infix notation indeed compiles to Clojure code and is equivalent to the above. |
| 71 | + |
| 72 | +(ys " |
| 73 | +defn LFree(mass): |
| 74 | + fn([_ _ v]): mass * 1/2 * square(v) |
| 75 | +") |
| 76 | + |
| 77 | +;; I proceed to the next infix |
| 78 | + |
| 79 | +(ys " |
| 80 | +defn sphere-to-R3(R): |
| 81 | + fn([_ [theta phi]]): |
| 82 | + up: |
| 83 | + =>: R * sin(theta) * cos(phi) |
| 84 | + =>: R * sin(theta) * sin(phi) |
| 85 | + =>: R * cos(theta) |
| 86 | +") |
| 87 | + |
| 88 | +;; which is the following in Clojure |
| 89 | + |
| 90 | +(kind/scittle |
| 91 | + '(defn sphere->R3 [R] |
| 92 | + (fn [[_ [theta phi]]] |
| 93 | + (up (* R (sin theta) (cos phi)) |
| 94 | + (* R (sin theta) (sin phi)) |
| 95 | + (* R (cos theta)))))) |
| 96 | + |
| 97 | +(do |
| 98 | + (defn call [f x] (f x)) |
| 99 | + (def of call) |
| 100 | + (def at call)) |
| 101 | + |
| 102 | +(ys " |
| 103 | +defn F-to-C(F): |
| 104 | + fn(state): |
| 105 | + up: |
| 106 | + time: state |
| 107 | + F: state |
| 108 | + =>: D(0).of(F).at(state) + ( D(1).of(F).at(state) * velocity(state) ) |
| 109 | +") |
| 110 | + |
| 111 | +(kind/scittle |
| 112 | + '(defn F->C [F] |
| 113 | + (fn [state] |
| 114 | + (up (time state) |
| 115 | + (F state) |
| 116 | + (+ (((D 0) F) state) |
| 117 | + (* (((D 1) F) state) |
| 118 | + (velocity state))))))) |
| 119 | + |
| 120 | +(ys " |
| 121 | +defn Lsphere(m R): |
| 122 | + compose: |
| 123 | + LFree: m |
| 124 | + F-to-C: sphere-to-R3(R) |
| 125 | +") |
| 126 | + |
| 127 | +(kind/scittle |
| 128 | + '(defn Lsphere [m R] |
| 129 | + (compose (Lfree m) (F->C (sphere->R3 R))))) |
| 130 | + |
| 131 | +(defmacro q [f] (list 'quote f)) |
| 132 | + |
| 133 | +(ys " |
| 134 | +simplify: |
| 135 | + Lsphere(m:q R:q): |
| 136 | + up: |
| 137 | + =>: t:q |
| 138 | + up: theta:q phi:q |
| 139 | + up: thetadot:q phidot:q |
| 140 | +") |
| 141 | + |
| 142 | +^:kindly/hide-code |
| 143 | +(defn show-expression [e] (kind/reagent [:tt e])) |
| 144 | + |
| 145 | +(show-expression |
| 146 | + '(simplify |
| 147 | + ((Lsphere 'm 'R) |
| 148 | + (up 't (up 'theta 'phi) (up 'thetadot 'phidot))))) |
| 149 | + |
| 150 | +(ys " |
| 151 | +defn L2(mass metric): |
| 152 | + fn(place velocity): mass * 1/2 * metric(velocity velocity).at(place) |
| 153 | +") |
| 154 | + |
| 155 | +(kind/scittle |
| 156 | + '(defn L2 [mass metric] |
| 157 | + (fn [place velocity] |
| 158 | + (* 1/2 mass ((metric velocity velocity) place))))) |
| 159 | + |
| 160 | +(def coordinate-system-to-vector-basis coordinate-system->vector-basis) |
| 161 | + |
| 162 | +(ys " |
| 163 | +defn Lc(mass metric coordsys): |
| 164 | + e =: coordinate-system-to-vector-basis(coordsys) |
| 165 | + fn([_ x v]): |
| 166 | + L2(mass metric): point(coordsys).at(x) (e * v) |
| 167 | +") |
| 168 | + |
| 169 | +(kind/scittle |
| 170 | + '(defn Lc [mass metric coordsys] |
| 171 | + (let [e (coordinate-system->vector-basis coordsys)] |
| 172 | + (fn [[_ x v]] |
| 173 | + ((L2 mass metric) ((point coordsys) x) (* e v)))))) |
| 174 | + |
| 175 | +(ys " |
| 176 | +the-metric =: literal-metric(g:q R2-rect) |
| 177 | +") |
| 178 | + |
| 179 | +(kind/scittle |
| 180 | + '(def the-metric (literal-metric 'g R2-rect))) |
| 181 | + |
| 182 | +(ys " |
| 183 | +L =: Lc(m:q the-metric R2-rect) |
| 184 | +") |
| 185 | + |
| 186 | +(kind/scittle |
| 187 | + '(def L (Lc 'm the-metric R2-rect))) |
| 188 | + |
| 189 | +(ys " |
| 190 | +simplify: |
| 191 | + L: |
| 192 | + up: |
| 193 | + =>: t:q |
| 194 | + up: x:q y:q |
| 195 | + up: vx:q vy:q |
| 196 | +") |
| 197 | + |
| 198 | +(show-expression |
| 199 | + '(simplify |
| 200 | + (L (up 't (up 'x 'y) (up 'vx 'vy))))) |
| 201 | + |
| 202 | +;; YAMLScript, no Clojars thus git-sha |
| 203 | + |
| 204 | +^:kindly/hide-code |
| 205 | +(kind/code " |
| 206 | +yamlscript/core {:git/url \"https://github.com/yaml/yamlscript\" |
| 207 | + :git/sha \"ed7adfbf90a39f379d5a7193bb2e4bdd7f0eecf8\" |
| 208 | + :deps/root \"core\"} |
| 209 | +") |
0 commit comments