diff options
author | Eduardo Julian | 2022-12-11 16:07:39 -0400 |
---|---|---|
committer | Eduardo Julian | 2022-12-11 16:07:39 -0400 |
commit | eef4422b1f16be2b8c651461f2c006dc4c11f314 (patch) | |
tree | 0fa040c7a628d03551b7d7d4244a4af025d5edba /stdlib/source/test/lux/math/arithmetic/modular.lux | |
parent | fd3f02c024687bc5c2b9741f6386719a0affb7bb (diff) |
Added support for fixed-point arithmetic.
Diffstat (limited to 'stdlib/source/test/lux/math/arithmetic/modular.lux')
-rw-r--r-- | stdlib/source/test/lux/math/arithmetic/modular.lux | 129 |
1 files changed, 129 insertions, 0 deletions
diff --git a/stdlib/source/test/lux/math/arithmetic/modular.lux b/stdlib/source/test/lux/math/arithmetic/modular.lux new file mode 100644 index 000000000..4d05bacbe --- /dev/null +++ b/stdlib/source/test/lux/math/arithmetic/modular.lux @@ -0,0 +1,129 @@ +(.require + [library + [lux (.except) + [abstract + [monad (.only do)] + [\\specification + ["$[0]" equivalence] + ["$[0]" order] + ["$[0]" monoid] + ["$[0]" codec]]] + [control + ["[0]" try] + ["[0]" exception] + [function + ["[0]" predicate]]] + [data + ["[0]" product] + ["[0]" bit (.use "[1]#[0]" equivalence)]] + [math + ["[0]" random (.only Random)] + [number + ["i" int]]] + [meta + ["[0]" type (.use "[1]#[0]" equivalence)]] + [test + ["_" property (.only Test)]]]] + [/// + ["//T" modulus]] + [\\library + ["[0]" / (.only) + [/// + ["//" modulus]]]]) + +(def .public (random modulus) + (All (_ %) + (-> (//.Modulus %) + (Random (/.Mod %)))) + (of random.monad each + (/.modular modulus) + random.int)) + +(def .public test + Test + (<| (_.covering /._) + (_.for [/.Mod]) + (do random.monad + [param::% (//T.random +1,000,000) + param (..random param::%) + + subject::% (random.only (predicate.and (|>> //.divisor (i.> +2)) + (|>> (//.= param::%) not)) + (//T.random +1,000,000)) + subject (..random subject::%) + another (..random subject::%)] + (`` (all _.and + (_.for [/.equivalence /.=] + ($equivalence.spec /.equivalence (..random subject::%))) + (_.for [/.order /.<] + ($order.spec /.order (..random subject::%))) + (,, (with_template [<composite> <monoid>] + [(_.for [<monoid> <composite>] + ($monoid.spec /.equivalence (<monoid> subject::%) (..random subject::%)))] + + [/.+ /.addition] + [/.* /.multiplication] + )) + (_.for [/.codec] + ($codec.spec /.equivalence (/.codec subject::%) (..random subject::%))) + + (_.coverage [/.incorrect_modulus] + (when (|> param + (of (/.codec param::%) encoded) + (of (/.codec subject::%) decoded)) + {try.#Failure error} + (exception.match? /.incorrect_modulus error) + + {try.#Success _} + false)) + (_.coverage [/.modulus] + (and (type#= (type_of (/.modulus subject)) + (type_of (/.modulus subject))) + (not (type#= (type_of (/.modulus subject)) + (type_of (/.modulus param)))))) + (_.coverage [/.modular /.value] + (/.= subject + (/.modular (/.modulus subject) (/.value subject)))) + (_.coverage [/.>] + (bit#= (/.> another subject) + (/.< subject another))) + (_.coverage [/.<= /.>=] + (bit#= (/.<= another subject) + (/.>= subject another))) + (_.coverage [/.-] + (let [zero (/.modular (/.modulus subject) +0)] + (and (/.= zero + (/.- subject subject)) + (/.= subject + (/.- zero subject))))) + (_.coverage [/.inverse] + (let [one (/.modular (/.modulus subject) +1) + co_prime? (i.co_prime? (//.divisor (/.modulus subject)) + (/.value subject))] + (when (/.inverse subject) + {.#Some subject^-1} + (and co_prime? + (|> subject + (/.* subject^-1) + (/.= one))) + + {.#None} + (not co_prime?)))) + (_.coverage [/.adapter] + (<| (try.else false) + (do try.monad + [copy::% (//.modulus (//.divisor subject::%)) + adapt (/.adapter subject::% copy::%)] + (in (|> subject + /.value + (/.modular copy::%) + adapt + (/.= subject)))))) + (_.coverage [/.moduli_are_not_equal] + (when (/.adapter subject::% param::%) + {try.#Failure error} + (exception.match? /.moduli_are_not_equal error) + + {try.#Success _} + false)) + ))))) |