# Elementary Slogan

In this chapter we will closely examine the basic constructs from which programs are built in Slogan. Like any other powerful language, Slogan allows us to combine these basic elements to build complex ones. We will also have a sneak peek at some of the means of abstractions offered by Slogan.1

## 3.1 Expressions

The preceding chapter showed how to use the REPL to interactively run code. The program fragments that you type in are called expressions. The Slogan interpreter responds by displaying the value of those expressions. One of the most primitive expression is a number. As there is nothing much to be done to a number in isolation, the interpreter will just give it back.

``````
2017
// 2017
``````

Numbers can be combined together using the familiar arithmetic operators to produce new values:

``````
2017 + 1
// 2018
1000 - 300 + 3
// 703
1000 - 300 * 3
// 100
4/2
// 2
``````

The arithmetic operators follow the commonly understood precedence and associativity rules. Multiplication and division takes precedence over addition and subtraction. The arithmetic operators with the same precedence associate from left to right. Parentheses are used to explicitly override precedence or group parts of an expression that should be evaluated first.

``````
(1000 - 300) * 3
// 2100
``````

There are many more operations you can perform on primitive data like numbers. These operations are all defined as functions. A function is usually invoked by calling its name followed by a list of arguments enclosed in parentheses. Examples of some useful numeric functions are given below:

``````
sqrt(1729)
// 41.58124577258358
mod(5, 2)
// 1
abs(-1)
// 1
sin(3.14)
// .0015926529164868282
``````

In fact, the arithmetic operators are all functions with special syntactic support from the language. The functions associated with the operators can be accessed by enclosing the operators in tick-quotes (```).

``````
`*`(10, 2)
// 20
`+`(1, 2, 3, 4, 5)
// 15
``````

In this section we have introduced two important concepts – expressions and values. A value is the result of an expression. To repeat the point with a simple example, `10 * 2` is not a value because a computation can still be performed on it. The result of that computation – the number `20` – is a value because no more operations can be performed on it.

### 3.1.1 Remembering Values

If we can associate a name with a value, it will be easier to refer to that value later. The names given to values are called variables. We name things with the `let` statement.2

``````
let rectangle_width = 23
let rectangle_length = 52
let rectangle_area = rectangle_width * rectangle_length

rectangle_area
// 1196
``````

The `let` statement is Slogan's simplest means of abstraction, for it allows to refer to results of complex computations by name.

The names that we use for variables are generally known as identifiers. Keywords, variables, and symbols are collectively called identifiers. Identifiers may be formed from letters, digits and these special characters: _, \$, %, and @. Some characters are reserved by the language for special purposes, mostly to be used as operators. The characters that cannot normally be used in identifiers are: +, -, /, *, <, ', >, =, \, #, ., (, ), {, }, [, ], ,, :, ; &, ? and |.

Identifiers are case-sensitive. For example, `rectangle_width` and `Rectangle_Width` are considered to be different identifiers. There is no inherent limit to the length of identifiers.

A number of identifiers are reserved by Slogan for syntactic definition. These are known as reserved words or keywords. They cannot be used as names for variables. The reserved words in Slogan are listed below:

``````
function
module
record
true
false
if
else
when
let
letfn
letrec
letdyn
yield
case
match
where
try
trycc
catch
finally
namespace
declare
assert
for
break
continue
``````

### 3.1.2 Grouping Expressions Together

It is possible to have multiple expressions evaluated in sequence and have a single value returned. Such groupings of expressions are known as code blocks. The expressions in a code block are enclosed in opening and closing curly braces. (`{ }`). The expressions in a code block is evaluated one after the other in the order they appear and the value of the final expression will be returned as the value of the entire block.

``````
{ showln(1 + 2)
showln(2 * 2)
sqrt(5 + 2) }
//> 3
//> 4
// 2.6457513110645907
``````

A code block is like any other expression that evaluates to a single value. It can appear wherever ordinary expressions are legal.

The scope of variables defined in a code block are limited to that code block. They won't be visible to code outside the block. All variable definition statements must appear at the top of the code block.

``````
let x = 100

{ let x = 200
x + 10 }
// 210

x + 10
// 110
``````

## 3.2 Defining Functions

The previous section described how values can be abstracted away by assigning them to variables. Function definitions are a more powerful abstraction mechanism by which an expression itself can be referenced by a name.

Imagine how you would express the conversion of temperature from Celsius to Fahrenheit. The procedure can be described in English as "multiply temperature in Celsius by 9, then divide by 5, then add 32". This description can be translated to a Slogan function as

``````
function celsius_to_fahrenheit(temperature)
temperature * 9 / 5 + 32
``````

A function definition is introduced by the `function` keyword. It is followed by the function's name. The `celsius_to_fahrenheit` function requires the caller to specify the temperature in Celsius that needs to be converted. This value becomes an entry in the parenthesized parameter list of the function. The parameter list is followed by an expression which is the formula for converting `temperature` to Fahrenheit. Unlike functions in imperative languages such as C, no explicit `return` statement is required to return a value from the function. The value of the last expression is implicitly returned as the value of the function call.

Here are a few instances of using the temperature conversion function:

``````
celsius_to_fahrenheit(180)
// 356
celsius_to_fahrenheit(30)
// 86
``````

Exercise 3.1.   Define a function to express the idea of squaring, i.e, multiplying a number `x` by itself.

Exercise 3.2.   Write a function that takes the radius of a circle as argument and return its area. The area of a circle is computed by the formula: `area = π × radius2`.

## 3.3 Comparison and Logical Operations

Slogan represent truth or Boolean values with the identifiers `true` and `false`. They are used as values for operations that return an yes or no answer. For instance, we can check if two values are equal and get back a Boolean result:

``````
1 == 1
// true
2 == 3
// false
``````

We can also do other kinds of comparisons like checking if a value is less than or greater than another value:

``````
1 < 2
// true
1 < 1
// false
1 <= 1 // less-than-or-equal-to
// true
1 > 2
// false
1 > 1
// false
1 >= 1 // greater-than-or-equal-to
// true

1 <> 2 // not-equals
// true
not(1 == 2)
// true

// like arithmetic operators, comparison operators are also real functions
`<`(1, 2, 3, 4, 5)
// true
`<`(1, 2, 3, 4, 4)
// false
`<=`(1, 2, 3, 4, 4)
// true
``````

Often we want to make a decision based on more than one Boolean value. The two logical operators - `&&` (`and`) and `||` (`or`) - are used for combining Boolean values.3

``````
1 < 2 && 2 == 2
// true
and(1 < 2, 2 == 2, 3 > 2)
// true
1 < 0 || 2 == 3 || 3 == 3
// true
or(1 < 0, 2 == 3, 3 > 4)
// false
``````

## 3.4 Conditional Expressions

Conditional expressions allows us to make a test and perform different operations based on the result of that test. The most general conditional is the `if` expression.4

The syntax of `if` is shown below:

``````
if (condition_expression)
consequent_expression
else
alternative_expression
``````

If `condition_expression` evaluates to `true`, `consequent_expression` is evaluated, otherwise `alternative_expression` is evaluated. The value of the expression that gets evaluated will become the value of the whole `if` expression.

Let us write a function that makes use of comparison operators and condition expressions. The function is called `reciprocal` and it computes `1/n` for a number `n` when it is not equal to `0`. If `n` is `0` `reciprocal` will return the string `"oops!"`.5

``````
function reciprocal(n)
if (n == 0) "oops!"
else 1/n
``````

Examples of using the `reciprocal` function are shown below:

``````
reciprocal(10)
// 1/10
reciprocal(1/10)
// 10
reciprocal(0)
// oops!
reciprocal(reciprocal(1/10))
// 1/10
``````

`Alternative_expression` can be another `if` expression, making it possible to check for multiple conditions. This is demonstrated by the next function which calculates train fare discounts based on the age and sex of the traveler. The rules for computing the discounts are these – if the traveler is female, give a `7%` discount, if the traveler is more than `60` years of age, add `12.5%` to the discount. The function takes the original fare, the age of the traveler and a Boolean value that indicates whether the traveler is female or not.

``````
function discount(fare, age, is_female)
if (is_female && age > 60) fare * (0.07 + 0.125)
else if (is_female) fare * 0.07
else if (age > 60) fare * 0.125
else 0

// Usage:
discount(1230, 61, true)
// 239.85
discount(1230, 42, true)
// 86.10000000000001
discount(1230, 42, false)
// 0
discount(1230, 63, false)
// 153.75
``````

`Alternative_expression` is optional. If it is omitted and `consequent_expression` evaluates to `false`, `if` will return `false`.

``````
if (1 < 2) 100
// 100
if (1 > 2) 100
// false
``````

The `when` expression is a cleaner alternative to `if` expressions without the `else` clause.

``````
when (1 < 2) 100
// 100
when (1 > 2) 100
// false
``````

### 3.4.1 The Truthfulness of Values

Though Slogan support two explicit identifiers to represent Boolean values, all values other than the identifier `false` is treated as true by the conditional expressions.

``````
if (1 + 2) "ok" else "no"
// ok
``````

Exercise 3.3.   Define a function that takes three numbers as arguments and returns the sum of the squares of the two larger numbers.

## 3.5 Repeating Yourself

Some problems require iterating over the same expressions for a given number of times. Most imperative languages provide constructs like the `for` and `while` loops for this purpose. Slogan gives you a simpler solution – if a function wants to repeatedly do some stuff, just make recursive calls to itself. If the recursive call is made at a position which is the last expression in the function, Slogan will arrange its internal affairs in such a way that the call stack won't overflow.

The next example defines a function that prints a table of Celsius to Fahrenheit conversions. It take three arguments - the lower limit of the table, the upper bound and the size by which each entry in the table differs.

``````
function print_temperature_table(lower, upper, size)
when (lower <= upper)
{ showln(lower, "c:", celsius_to_fahrenheit(lower), "f")
print_temperature_table(lower + size, upper, size) }
``````

This function makes use of the `celsius_to_fahrenheit` function we defined earlier. `Print_temperature_table` will call itself until the limit is reached. This recursive call is made as the last expression in the conditional block. This also happens to be the last expression executed by the function. So Slogan translates this into an iterative call, removing the previous call stacks from the call frame. This optimization allows the function to call itself as many times as it wants and no special looping construct is needed.6

Before we move to the next topic, let us once see the `print_temperature_table` in action:

``````
print_temperature_table(0, 100, 20)
//> 0c:32f
20c:68f
40c:104f
60c:140f
80c:176f
100c:212f
``````

Exercise 3.4.   Read the Wikipedia article on ancient Egyptian multiplication. Use recursion to implement one of the algorithms described there.

## 3.6 Time Server Revisited

Now we know enough about Slogan to fix the first problem that our time server had – its inability to handle more than a single client. This can be fixed using recursion. We will put the basic behavior of the server in a function that calls itself for handling each client.

``````
// file: time_server02.sn

let server = tcp_server_stream(2121)

function client_handler()
{ let client = read(server)
let request = read_line(client)
if (request == "GET TIME")
showln(stream = client, time_to_string(now()))
else
showln(stream = client, "error: invalid request")
close_stream(client)
// call self to handle next client
client_handler() }

// start the handler
client_handler()
// we will never reach here
close_stream(server)
``````

To try the new server, load the `time_server02.sn` script into the REPL:

``````
``````

Start another REPL and load the client `time_client.sn` script. To send multiple requests to the server, just reload the client multiple times. The new server will be able to handle these requests without requiring a restart. A significant improvement indeed!

``````
//> 2017-04-30T08:00:48
//> 2017-04-30T08:00:49
``````

As the server always expects another client to connect, it will never terminate. You can terminate the server process by pressing the `Control+C` key-combination in the shell that the server is running.

1Starting from this chapter, we will only show code snippets and their output without the `slogan>` prompt. You may evaluate the programs interactively at the REPL or type them into a file that is compiled and executed later. While using the REPL, remember to end all expressions with a semicolon (`;`), so that the interpreter can kick-in and evaluate that expression. Semicolons are normally not required to terminate expressions entered into a file. So we omit them in the code examples as well.

2A statement is often defined as code that does something and does not produce a value. Slogan do not have statements in this sense, it only have expressions. Even statements like `let` return a value. This value is a special object known as `void`. So, in the context of Slogan, a statement is an expression that returns `void`.

3`&&` takes precedence over `||`.

4`If` is an expression because it returns the value of the expression that was conditionally evaluated. This may come as a surprise for some among the readers as most popular languages treat conditionals as statements.

5The string data type will be covered in detail in the next chapter.

6Slogan do have a built-in imperative looping construct which is similar to the `for` loop in C. But Slogan's `for` loop is more powerful and expressive, as you will discover later. It is also possible to add new looping constructs to the language using the syntactic extension facility. Despite all this, the preferred way to repeatedly execute a piece of code in Slogan is by tail-recursion!