(.using [library [lux (.except) [extension (.only analysis)] ["@" target] ["[0]" static] [abstract ["[0]" monad (.only do)]] [control ["[0]" try (.only Try)] ["[0]" exception (.only exception:)] ["<>" parser (.only) ["<[0]>" code]]] [data [text ["%" format]] [collection ["[0]" list (.open: "[1]#[0]" mix)]]] [macro [syntax (.only syntax)] ["[0]" template]] [tool [compiler ["[0]" phase (.open: "[1]#[0]" monad)] [language [lux ["[0]" analysis (.only Analysis Operation Phase) ["[0]" type]]]] [meta [archive (.only Archive)]]]] [type ["[0]" check]]]] [/ ["[0]" random] [number ["[0]" nat] ["[0]" int] ["[0]" rev] ["[0]" frac] ["[0]" ratio (.only Ratio)] ["[0]" complex (.only Complex)]]]) (exception: (no_arithmetic_for [type Type]) (exception.report "Type" (%.type type))) (def: (composite phase archive <+> last prevs) (-> Phase Archive Code Analysis (List Analysis) (Operation Analysis)) (case <+> [_ {.#Text $}] (phase#in (list#mix (function (_ left right) {analysis.#Extension $ (list left right)}) last prevs)) _ (do phase.monad [[_ $] (type.inferring (phase archive <+>))] (in (list#mix (function (_ left right) (analysis.reified [$ (list left right)])) last prevs))))) (for @.old (these) (with_expansions [<@> (static.text (let [[@ _] (symbol .._)] @)) [ratio.#numerator 0 ratio.#denominator 1] [ratio.#numerator 1 ratio.#denominator 1] [complex.#real +0.0 complex.#imaginary +0.0] [complex.#real +1.0 complex.#imaginary +0.0]] (these (with_template [ '] [(with_expansions [ (static.seed) (template.text [<@> " " ]) (template.spliced ')] (these (analysis ( self phase archive [operands (<>.some .any)]) (<| type.with_var (function (_ [$it :it:])) (do [! phase.monad] [operands (monad.each ! (|>> (phase archive) (type.expecting :it:)) operands) _ (type.inference :it:) :it: (type.check (check.identity (list) $it))] (case (list.reversed operands) (pattern (list single)) (in single) (pattern (list)) (`` (cond (check.subsumes? .I64 :it:) (phase.except ..no_arithmetic_for [:it:]) (~~ (with_template [ <0> <+>] [(check.subsumes? :it:) <0>] )) ... else (phase.except ..no_arithmetic_for [:it:]))) (pattern (list.partial last prevs)) (`` (cond (check.subsumes? .I64 :it:) (phase.except ..no_arithmetic_for [:it:]) (~~ (with_template [ <0> <+>] [(check.subsumes? :it:) (..composite phase archive (` <+>) last prevs)] )) ... else (phase.except ..no_arithmetic_for [:it:]))))))) (def: .public (syntax (_ [operands (<>.some .any)]) (in (list (` ( (~+ operands)))))))))] [+ [[.Nat (in (analysis.nat 0)) "lux i64 +"] [.Int (in (analysis.int +0)) "lux i64 +"] [.Rev (in (analysis.rev .0)) "lux i64 +"] [.Frac (in (analysis.frac +0.0)) "lux f64 +"] [Ratio (type.expecting Ratio (phase archive (` ))) ratio.+] [Complex (type.expecting Complex (phase archive (` ))) complex.+]]] [- [[.Nat (in (analysis.nat 0)) "lux i64 -"] [.Int (in (analysis.int -0)) "lux i64 -"] [.Rev (in (analysis.rev .0)) "lux i64 -"] [.Frac (in (analysis.frac -0.0)) "lux f64 -"] [Ratio (type.expecting Ratio (phase archive (` ))) ratio.-] [Complex (type.expecting Complex (phase archive (` ))) complex.-]]] [* [[.Nat (in (analysis.nat 1)) nat.*] [.Int (in (analysis.int +1)) "lux i64 *"] [.Rev (in (analysis.rev rev./1)) rev.*] [.Frac (in (analysis.frac +1.0)) "lux f64 *"] [Ratio (type.expecting Ratio (phase archive (` ))) ratio.*] [Complex (type.expecting Complex (phase archive (` ))) complex.*]]] [/ [[.Nat (in (analysis.nat 1)) nat./] [.Int (in (analysis.int +1)) "lux i64 /"] [.Rev (in (analysis.rev rev./1)) rev./] [.Frac (in (analysis.frac +1.0)) "lux f64 /"] [Ratio (type.expecting Ratio (phase archive (` ))) ratio./] [Complex (type.expecting Complex (phase archive (` ))) complex./]]] ) (with_template [ '] [(with_expansions [ (static.seed) (template.text [<@> " " ]) (template.spliced ')] (these (analysis ( self phase archive [left .any right .any]) (<| type.with_var (function (_ [$it :it:])) (do [! phase.monad] [left (type.expecting :it: (phase archive left)) right (type.expecting :it: (phase archive right)) _ (type.inference .Bit) :it: (type.check (check.identity (list) $it))] (`` (cond (check.subsumes? .I64 :it:) (phase.except ..no_arithmetic_for [:it:]) (~~ (with_template [ <+>] [(check.subsumes? :it:) (..composite phase archive (` <+>) right (list left))] )) ... else (phase.except ..no_arithmetic_for [:it:])))))) (def: .public (syntax (_ [left .any right .any]) (in (list (` ( (~ left) (~ right)))))))))] [= [[.Nat "lux i64 ="] [.Int "lux i64 ="] [.Rev "lux i64 ="] [.Frac "lux f64 ="] [Ratio ratio.=] [Complex complex.=]]] [< [[.Nat nat.<] [.Int "lux i64 <"] [.Rev rev.<] [.Frac "lux f64 <"] [Ratio ratio.<]]] [> [[.Nat nat.>] [.Int int.>] [.Rev rev.>] [.Frac frac.>] [Ratio ratio.>]]] [<= [[.Nat nat.<=] [.Int int.<=] [.Rev rev.<=] [.Frac frac.<=] [Ratio ratio.<=]]] [>= [[.Nat nat.>=] [.Int int.>=] [.Rev rev.>=] [.Frac frac.>=] [Ratio ratio.>=]]] ) (with_template [ '] [(with_expansions [ (static.seed) (template.text [<@> " " ]) (template.spliced ')] (these (analysis ( self phase archive [left .any right .any]) (<| type.with_var (function (_ [$it :it:])) (do [! phase.monad] [left (type.expecting :it: (phase archive left)) right (type.expecting :it: (phase archive right)) _ (type.inference :it:) :it: (type.check (check.identity (list) $it))] (`` (cond (check.subsumes? .I64 :it:) (phase.except ..no_arithmetic_for [:it:]) (~~ (with_template [ <+>] [(check.subsumes? :it:) (..composite phase archive (` <+>) right (list left))] )) ... else (phase.except ..no_arithmetic_for [:it:])))))) (def: .public (syntax (_ [left .any right .any]) (in (list (` ( (~ left) (~ right)))))))))] [% [[.Nat nat.%] [.Int "lux i64 %"] [.Rev rev.%] [.Frac "lux f64 %"] [Ratio ratio.%] [Complex complex.%]]] ) )))