## Syntax

The goal of Passerine's syntax is to make all expressions as *concise* as possible while still conserving the 'feel' of *different types* of expressions.

We'll start simple; here's a function that squares a number:

```
square = x -> x * x
square 4 -- is 16
```

By the way: Passerine uses

`-- comment`

for single-line comments and`-{ comment }-`

for nestable multi-line comments.

There are already some important things we can learn about Passerine from this short example:

Like other programming languages, Passerine uses `=`

for assignment. On the left hand side is a *pattern* – in this case, just the variable `square`

– which destructures an expression into a set of bindings. On the right hand side is an *expression*; in this case the expression is a *function definition*.

Because Passerine is

expression-oriented, the distinction between statements and expressions isn't made. In the case that an expression produces no useful value, it should return the Unit type,`()`

. Assignment, for instance, returns Unit.

The function call `square 4`

may look a bit alien to you; this is because Passerine uses whitespace for function calls. A function call takes the form `l e₀ ... eₙ`

, where `l`

is a function and `e`

is an expression. `square 4`

is a simple case because `square`

only takes one argument, `x`

... let's try writing a function that takes two arguments!

Using our definition of `square`

, here's a function that returns the Euclidean distance between two points:

```
distance = (x1, y1) (x2, y2) -> {
sqrt (square (x1 - x2) + square (y1 - y2))
}
origin = (0, 0)
distance origin (3, 4) -- is 5
```

Passerine is an *expression-oriented* language, because of this, it makes sense that *all functions are anonymous*. All functions take the form `p₀ ... pₙ -> e`

, where `p`

is a pattern and `e`

is an expression. If a function takes multiple arguments, they can be written one after another; `a b c -> d`

is equivalent to `a -> (b -> (c -> d))`

.

The function `distance`

is a bit more complex that `square`

, because the two arguments are bound using *tuple destructuring*.

As you can see, `distance`

takes two pairs, `(x1, y1)`

and `(x2, y2)`

, and *destructures* each pair into its component parts. For instance, when we call `distance`

in `distance origin (3, 4)`

the function pulls out the numbers that make up the pair:

`origin`

, i.e.`(0, 0)`

, is matched against`(x1, y1)`

, creating the bindings`x1 = 0`

and`y1 = 0`

.- the tuple
`(3, 4)`

is matched against`(x2, y2)`

, creating the bindings`x2 = 3`

and`y2 = 4`

.

The body of `distance`

, `sqrt (...)`

is then evaluated in a new scope where the variables defined about are bound. In the case of the above example:

```
-- call and bind
distance origin (3, 4)
distance (0, 0) (3, 4)
-- substitute and evaluate
sqrt (square (0 - 3) + square (0 - 4))
sqrt (9 + 5)
sqrt 25
5
```

Now, you may have noticed that `distance`

is actually two functions. It may be more obvious it we remove some syntactic sugar rewrite it like so:

```
distance = (x1, y1) -> { (x2, y2) -> { ... } }
```

The first function binds the first argument, then returns a new function that binds the second argument, which evaluates to a value. This is known as *currying*, and can be really useful when writing functional code.

To leverage currying, function calls are

left-associative. The call`a b c d`

is equivalent to`((a b) c) d`

, not`a (b (c d))`

. This syntax comes from functional languages like Haskell and OCaml, and makes currying (partial application) quite intuitive.

In the above example, we used `distance`

to measure how far away `(3, 4)`

was from the origin. Coincidentally, this is known as the *length* of a vector. Wouldn't it be nice if we could define length in terms of distance?

```
length = distance origin
length (5, 12) -- is 13
```

Because distance is curried, we can call it with only one of its arguments. For this reason, `length`

is a function that takes a pair and returns its distance from the `origin`

. In essence, we can read the above definition of `length`

as:

`length`

is the`distance`

from`origin`

.

Transforming data through the use of and functions and pattern matching is a central paradigm of Passerine. In the following sections, we'll dive deep and show how this small core language is enough to build a powerful and flexible language.