Crates.io | polenta |
lib.rs | polenta |
version | 0.1.1 |
source | src |
created_at | 2024-09-17 19:10:38.892476 |
updated_at | 2024-09-17 19:30:01.589006 |
description | A toy language about polynomials over finite-fields |
homepage | |
repository | |
max_upload_size | |
id | 1377884 |
size | 57,694 |
Polenta is a toy polynomial arithmetic language, and everything is a polynomial. As such, it is more suited towards having fun instead of having performance.
let
and assert
expressionsprove
and commit
expressionsThe project mostly started to learn more about Pest, and it is a lovely project! See https://pest.rs for more!
You can add the library with:
cargo add polenta
You can install the REPL with:
cargo install polenta --bin repl --features="repl"
In this section we go over what can be done with Polenta.
All code shown below are valid Polenta code. To follow along, you can use the REPL installed above!
You can use Polenta as a calculator-over-field.
> 10 - 2^3 * 2;
18446744069414584315
However, you should keep in mind that all operations are defined over the field, so division might not always work as you expect:
> 1 / 2; // some number x such that 2*x = 1, not 0.5!
9223372034707292161
Polenta supports single line comments using
//
, as shown above.
A polynomial is created by specifying its terms.
> let P(x) = 3*x^2 + 5;
3*x^2 + 5
Behind the scenes all terms are considered a monomial, and they are composed together. As such, you can repeat a term with the same degree and the result will have them added up:
> let P(x) = 3*x^2 + 2*x^2 + 1*x^2;
6*x^2
> let Q(x) = 5*x - 5*x + 1;
1
You can also multiply polynomials:
> let P(x) = (x + 1)*(x + 2)*(x + 4);
x^3 + 7*x^2 + 14*x + 8
You can create a polynomial from an existing one:
> let P(x) = 3*x;
3*x
> let Q(x) = P^2 + 2*P;
9*x^2 + 6*x
Shadowing is allowed:
> let P(x) = 3*x;
3*x
> let P(x) = 3*P + 5;
9*x + 5
You can use an identifier within a polynomial, but if the identifier has the same name as the term, it will be ignored.
> let t = 2;
> let x = 5;
> let P(x) = x^t + 2*x;
x^2 + 2*x
Polenta has ==
and !=
operators that return either a 1 or 0 based on the equality.
> 2 == 3
0
> let P(x) = 2*x
2*x
> let Q(x) = 3*x - x
2*x
> P == Q
1
Evaluation is achieved using a binary operation @
, so that P@2
means "evaluate polynomial P
at point 2
.
> let P(x) = 3*x;
3*x
> let z = P@3;
9
> let Q(x) = x^z + z*x;
x^9 + 9*x
Remember that everything is a polynomial in Polenta, so you could evaluate a number as well. Evaluation will not have an effect because a number is treated as a constant polynomial.
> 4@2
4
Since evaluation is a binary operation, you can chain them together:
> let P(x) = 3*x + 1;
3*x + 1
> let Q(x) = x/2;
9223372034707292161*x
> Q@P@Q@P@3; // Q(P(Q(P(3))))
8
You can make assertions within Polenta for safety, where a failed assertion throws an AssertionError
.
An assertion fails if the expression that they are given is a zero polynomial.
> assert 1
1
> assert 0
× Assertion Failed
> assert 43
43
While using REPL, if there is an error you will see it on screen with clear logs.
> let x = idontexist;
× Unknown Identifier: idontexist
> 5/0;
× Division by Zero
> let a = ++syntaxerror--;
× Syntax Error
╭─[input:1:9]
1 │ let a = ++syntaxerror--;
· ─
╰────
help: Expected one of [expr], got []
Run all tests with:
cargo test
Polenta is MIT licensed.