Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
This is currently in-development vaporware.
Celerity is a programming language aiming for a good balance of productivity and scalability while being easily embeddable in host applications.
Celerity is expression-oriented, multi-paradigm, and features optional type checking. Some notable features are pattern matching, first-class functions with closures, opt-in mutability, explicit yet terse error propagation, concurrency based on lightweight agents, and non-suspending garbage collection.
Celerity can be installed as a .NET tool in two ways:
To install Celerity globally, run dotnet tool install celerity -g
. This will allow you to run the celerity
CLI driver anywhere, assuming you have set up your PATH
appropriately.
To install Celerity locally in a .NET-based project with a tool manifest, omit the -g
option. This will require you to run dotnet celerity
from the project directory.
unk
is a special type that, like any
, allows any value. Unlike any
, however, unk
only allows a very limited set of operations which are safe on all values. In other words, unk
is the type-safe counterpart to any
.
A value of type unk
can only be assigned to a location of type unk
or any
.
any
is a special type that, like unk
, allows any value. Unlike unk
, however, any
allows you to perform any operation on the value, even if the type checker would otherwise be able to prove that a given operation is incorrect.
The type of any operation on a value typed as any
is also any
. A value of type any
can be assigned to a location of any other type.
unk
should generally be preferred over any
wherever possible.
Evaluates expression
(the initializer) and matches it against pattern
. If the match fails, a panic occurs.
Any bindings in pattern
are available for the remainder of the enclosing block expression. Any bindings in pattern
that existed prior to the let
statement are shadowed for the remainder of the enclosing block expression.
Evaluates expression
(the value). If the expression statement is the final statement of the enclosing block expression, the value becomes the result of the block expression.
Defers evaluation of expression
(the body) until control leaves the enclosing block expression. Multiple defer
statements are evaluated in reverse lexical order.
defer
statements are typically used to reliably clean up resources regardless of how control leaves a block expression.
For each condition-expression-arm
, in lexical order, evaluates the first expression
(the condition). The first condition that tests as truthy causes the associated second expression
(the body) to be evaluated and the evaluation of arms to stop. If no body is evaluated during this process, a panic occurs.
The whole expression results in the value of the evaluated body.
Evaluates the expression
(the condition). If the result tests as truthy, the first block-expression
(the then body) is evaluated. Otherwise, if an if-expression-else
clause is present, the second block-expression
(the else body) is evaluated.
The whole expression results in one of the following values, in order:
The result of the then body.
The result of the else body, if an if-expression-else
is present.
The nil value.
Almost all values are considered truthy, with the following exceptions:
The nil value.
The false
Boolean value.
Stops the evaluation of the enclosing while
expression or for
expression. In other words, a break
expression is semantically equivalent to transferring control to just after the final statement of the loop body, and then performing no further iterations. If a break-expression-result
is present, the expression
(the result) becomes the result of the enclosing while
expression or for
expression.
Any defer
statements that would go out of scope due to the control transfer are executed before stopping the loop.
It is a semantic error for a break
expression to appear outside of the loop body of a while
expression or for
expression. If a break
expression appears in the body of a defer
statement, it cannot bind to a while
expression or for
expression outside of the body.
A break
expression has no result value.
Evaluates the first block-expression
(the loop body) repeatedly until the expression
(the condition) no longer tests as truthy. The condition is evaluated at the beginning of every iteration. If no iterations run and a while-expression-else
is present, the second block-expression
(the else body) is evaluated once.
The whole expression results in one of the following values, in order:
The result of any break as
expression within the loop body.
The result of the loop body, if at least one iteration completes.
The result of the else body, if a while-expression-else
is present.
The nil value.
Evaluates expression
(the result), explicitly returns result from the current fn
declaration or lambda expression, and transfers control back to the caller.
Any defer
statements that would go out of scope due to the control transfer are executed after evaluating result, but before returning it to the caller.
It is a semantic error for a ret
expression to appear outside of an fn
declaration or lambda expression. A ret
expression cannot appear in the body of a defer
statement, unless it is nested in a lambda expression.
A ret
expression has no result value.
Skips the remaining portion of the loop body of the enclosing or and starts a new iteration. In other words, a next
expression is semantically equivalent to transferring control to just after the final statement of the loop body.
Any that would go out of scope due to the control transfer are executed before the next loop iteration is started.
It is a semantic error for a next
expression to appear outside of the loop body of a while
expression or for
expression. If a next
expression appears in the body of a defer
statement, it cannot bind to a while
expression or for
expression outside of the body.
A next
expression has no result value.
Evaluates expression
(the condition). If the result does not test as truthy, a panic occurs. An assert
expression is always executed; it is not conditional on build flags or similar.
An assert
expression is typically used in a test
declaration to verify the outcome of a unit test, but it can also be used in regular code. The runtime system is allowed to optimize with the assumption that condition holds after the assert
expression.
The result of an assert
expression is the value of the condition.