Learn Elixir

Introduction to Elixir Programming

Welcome to the Elixir programming language tutorial.

The Elixir programming language runs on top of the Erlang VM. It’s compatible with Erlang, but has a different syntax and features.

Programming is a field in which it feels like each and every day a new language, library or framework is discovered.

Usually, it is rather difficult to keep up with the innovations, but when communities worldwide recommend a certain novelty, it is worth checking and experimenting with it. This is also the case with the Elixir programming language.

So, when it comes to choosing a functional programming language, there are available a multitude from which you can choose depending on what you need.

Elixir Programming Language

Elixir is a functional programming language that gains more and more popularity in developers’ community. It is considered to be an immutable functional language, which basically signifies the fact that is easy to read and build on, a dream came true for any respectable programmer.

Concurrency

The primary purpose of Elixir programming is concurrency. Concurrency refers to the efficiency with which a vast number of processes can be run at the same time, without being related to one another, while diminishing side effects.

Erlang Virtual Machine

Elixir has as a primary benefit the fact that it can be used with the Erlang Virtual Machine or EVM. What is even more interesting is that Elixir processes steer clear of problems associated with managing share data by simply getting rid of shared memory and counting on asynchronous message passing.

Moreover, the manner in which the processes can connect with each other across the same network, recommends Elixir as a great tool for horizontal scaling, similar to that used in distribute systems.

As mentioned above, Elixir programming language had a success in EVM, while the Erlang community openly accepted Elixir due to its scalable and maintainable applications.

Thus, Elixir gained access to the Erlang ecosystem, functions and benefits of its VM that leads to low-latency, fault-tolerance and distributed systems.

what is elixir

Syntax

Elixir code is easy to implement, a lightweight solution for using efficiently machine resources.

You can start the Elixir interactive shell with the command iex.

Interactive Elixir (1.3.3) - press Ctrl+C to exit (type h() ENTER for help)
iex(1)> IO.puts("Hello world")
hello world

To run Elixir code from a file use:

elixirc hello.ex

Why Elixir?

So, the question that remains is why you should try and use Elixir programming language. Well, Elixir forums provide a detailed perspective in regards to this new language, while recommending it as a tool you can rely on when it comes to web-related or distributed actions.

Furthermore, the tendency nowadays is to set up distributed software, being considered more efficient and reliable, for which a new programming language such as Elixir is preferred due to the fact that it permits developers to establish a distribute-style software from the foundation up.

Bottom line, Elixir programming represents a dynamic, functional language built up for scalable and maintainable applications.

Also, Elixir is much better than Erlang VM, commonly known for its low-latency and fault-tolerant systems, which users now tend to avoid.

Elixir can be successfully used in both web development and software domains, due to its scalability, extensibility and functional programming.

Install Elixir

The installation of elixir is relatively simple, and this article focuses on how to install and use elixir on a linux system.

In fact, the official website has already introduced the installation on the official website in detail, so I won’t elaborate on it here. Just know that elixir is based on erlang so

Before installing elixir, make sure that erlang is installed locally and that elixir is only compatible with versions of erlang 18 and later.

Because of the linux system package management tools are diverse, so I recommend the source code compilation is more general.

$ git clone https://github.com/elixir-lang/elixir.git

Executing the above command in the terminal will get the elixir source code in the current directory, of course, careful people can imagine that when we check the version, we find

$ cd elixir
$ cat VERSION
1.5.0-dev

‘-dev’ means that the current branch is a development branch and not a stable version, of course if you just want to try it out you can skip a step. If we need to use it for an actual project then we must use this version of Stable. The good thing is that this is a git repository, we just need to know that the current stable version is switching over at that branch

$ git branch -a 
* :: master
  origin
  remotes/origin/HEAD -> origin/master
  remotes/origin/jf-genserver
  remotes/origin/master
  remotes/origin/v1.0
  remotes/origin/v1.1
  remotes/origin/v1.2
  remotes/origin/v1.3
  remotes/origin/v1.4

Now the stable version of elixir is up to 1.4 so (git is good for version control)

$ git checkout origin/v1.4
$ cat VERSION
1.4.2

The next step is to compile and install, first go to the source code directory and then execute the following command

$ make clean test
$ make install

This process is a bit long, go to make a cup of tea and come back on everything OK sometimes encounter testing errors, you can follow the specific tips google a bit, generally can solve. Well, when you run IEX in the terminal and see the following, you’re done

Erlang/OTP 18 [erts-7.3] [source] [64-bit] [smp:8:8] [async-threads:10] [hipe] [kernel-poll:false]

Interactive Elixir (1.4.1) - press Ctrl+C to exit (type h() ENTER for help)

iex(1)> 

Since elixir provides a very handy co-build tool, mix, when we want to build a new project we just need

$ mix new my_project
$ cd my_project

Once you’re in the directory, you can clearly see the structure of the directory, and then you can start the elixir journey!

Hello world

Hello world program in Elixir. This program only outputs hello world.
Save as helloworld.ex, then run it in the command line.

defmodule Hello do
   def sample do
       IO.puts "Hello World!"
   end
end

The program creates a module with one function. To run it, load the program and then call the method using the module. As shown below:

Hello world

Run with this the elixir interactive shell:

iex
Erlang/OTP 20 [erts-9.2] [source] [64-bit] [smp:4:4] [ds:4:4:10] [async-threads:10] [kernel-poll:false]

Interactive Elixir (1.3.3) - press Ctrl+C to exit (type h() ENTER for help)
iex(1)> c("helloworld.ex")
[Hello]
iex(2)> Hello.sample
Hello World!
:ok
iex(3)> 

hello world in elixir

Variables

Variables in Elixir can be defined easily. A variable can be of a variety of types includes numbers and words.

You can try this in the Elixir interactive shell, iex:

iex(1)> x = 3
3

iex(2)> name = "Bob"
name

Or if you want to output it as text:

iex> name = "Alice"
"Alice"
iex> "Your name is, #{name}"
"Your name is, Alice"

Data types

A variable can be of a certain type, like strings (words), integers (whole numbers), booleans (true/false values)

Elixir has several types of variables that are supported, namely:

  • integers
  • float
  • boolean
  • atom/symbol
  • string
  • list
  • tuple

In the Elixir interactive shell:

iex> 1         # integer
iex> 0x1F      # integer (hexadecimal)
iex> 1.0       # float, because the dot
iex> true      # boolean
iex> :atom     # aom
iex> "elixir"  # string
iex> [1,2,3]   # list
iex> {1,2,3}   # tuple

Arithmetics

In the Elixir shell (iex) you can type any expression

iex> 4+4
8
iex> 3*3
9
iex> 10 / 2
5.0

In the top two examples an integer is returned (8,9) but in the last example
a floating point number (5.0). Why?

Because in Elixir the division operator (/) always returns a float. But you can round the output to the nearest number using:

round(10/2)
5

Elixir Strings

UTF-8

Elixir strings are encoded in UTF-8 format. That means all the special characters of UTF-8 are supported out of the box.

iex> "hellö wörld 由力驱动"
"hellö wörld 由力驱动"

This can be done with variables to:

iex> x = "hello"
"hello"
iex> x
"hello"

You can print variables like this

iex> x = 3
iex> IO.puts("x = #{x}")

Newline

Line breaks are also supported by using the \n character.

iex> IO.puts("hello\nworld\nhello\nyou")
hello
world
hello
you

If you try it without IO.puts, it will show you the string definition without newlines:

"hello\world\nhello\nyou"

String length

To get the string length

iex> String.length("hello world")

The length can be assigned to a variable:

iex> sl = String.length("hello world")
iex> sl

Functions

Functions are at the heart of programming in Elixir. How do you create functions and how do you use them?

In this article you’ll learn how to use named functions. This is not the only type of function, as you will learn in the next lesson.

Function example

Function call

A function is created in a module. You can do this directly from Elixir shell (iex) or create a file (.ex) and run it with elixirc.

The sample below defines a module (Hello) and a named function (hello) that doesn’t take any arguments.

defmodule Hello do
  def hello do
    IO.puts "hello world"
  end
end

A function is defined with the def keyword, it should be inside a module defined with the defmodule keyword.

Don’t forget the do end combination as this defines the code block (scope).

Then call it (the function call) using:

iex> Hello.hello
hello world
:ok

Because the named function only has one line, you can shorten it to:

defmodule Hello do
  def helo do IO.puts "hello world" end
end

Which does exactly the same, but sometimes a one liner is easier to read.

Function parameters

Functions can take parameters. Let’s start by creating a function that takes parameters a and b.

defmodule Maths do
  def sum(a,b) do
    a + b
  end
end

Then call it with

iex> Maths.sum(3,4)
7

If statements

If statements execute an expression if it’s condition is true. The expression is executed if and only if the condition (sometimes called predicate) is true.

The if statement is a key concept in programming that exists in many other languages. But, unlike traditional languages elixir variables are immutable.

elixir if

In elixir the condition is written between the words if and do. The expression is not executed if the condition is false.

You can use if statements in the Elixir interactive shell or from elixir code.

x = 3

if x > 2 do
 " x greater than 2"
end

elixir if else

If the condition is not true, it can be false. You can use if else to capture both cases.

if false do
  "This will never be seen"
else
  "This will"
end

In elixir interactive shell:

~ iex
Erlang/OTP 20 [erts-9.2] [source] [64-bit] [smp:4:4] [ds:4:4:10] [async-threads:10] [kernel-poll:false]

Interactive Elixir (1.3.3) - press Ctrl+C to exit (type h() ENTER for help)
iex(1)> if false do
...(1)>   "can not be here"
...(1)> end
nil

if statement in elixir

elixir if else one line

You can use a one liner for if statements like this:

if true, do: :ok, else: :error

In elixir interactive shell:

iex(4)> if true, do: :ok, else: :error
:ok

Anonymous functions

Anonymous functions are defined on a single line. In Elixir, an anonymous function is a basic type. You may have guessed, anonymous functions don’t have a name.

In functional programming, you want to transform data and that’s what functions are for. Elixir has two types of functions: anonymous functions and named functions.

Declare Anonymous Function

To define one, write fn (ArgumentList) -> body end.

It has these parts:

  • fn the declaration

  • (ArgumentList) zero or more arguments (we’ll use a and b).

  • -> function implementation starts here

  • end declaration ends

You can check verify it’s indeed a function with

iex> is_function(double)
true

Create Anonymous function

Start the Elixir shell (iex) to try the examples below. The example below creates an anonymous function that takes parameters a and b.

iex> sumit= fn(a,b) -> a+b end
iex> sumit.(2,3)
5

To call anonymous function, the expression sumit.(2,3) is used.

The dot in sumit.(2,3) is required for anonymous functions. This is how Elixir distincts anonymous functions from named functions.

iex> double= fn a -> add.(a,a) end
iex> double.(2)
4

The anonymous function is stored in double. Then it’s called with double.(2).

Anonymous function name

The function assigned to the variable can change, take a look at this example:

iex> func = fn(a,b) -> a+b end
iex> func.(5,3)
8
iex> func = fn(a,b) -> a-b end
iex> func.(5,3)
2

In this example func is a variable, not a function name. The anonymous function assigned to it is reassigned, that’s why the output changes when calling it.

You can change them anytime you’d like, whoa!

Case

Case is used to compare a value against many patterns until a matching one is found. This is similar to the switch statements in other programming languages.

Given an input variable, it will copmare it to every pattern. There are some examples below.

elixir case pattern matching

Elixir checks for a matching pattern. You can try this in iex:

iex(1)> case {1,2,3} do
...(1)>   {1,5,6} -> "156"
...(1)>   {1,2,4} -> "124"
...(1)>   {1,2,3} -> "123"
...(1)> end
"123"

elixir case example

Start the Elixir interactive shell iex in the terminal.
Then try the elixir case example below:

Interactive Elixir (1.3.3) - press Ctrl+C to exit (type h() ENTER for help)
iex(1)> x = 3
3
iex(2)> case {x} do
...(2)>   {1,2} -> "No match"
...(2)>   {3} -> "Match"
...(2)> end
"Match"

As you see, only expression where x is equal to 3 is executed. You can specify a pattern of possibilites with case.

If the value is not in the pattern, it will give a CaseClauseError. Like so:

iex(3)> case {x} do
...(3)>   {4} -> "Four"
...(3)> end
** (CaseClauseError) no case clause matching: {3}

Cond

Cond lets you check many conditions at the same time.

If a condition in the block is true, its code will be executed. If the condition is not true, it will simply go to the next condition.

This is repeated until either the end of the block or until a codition is true.

cond example

You can try this in the elixir interactive shell iex:

iex(1)> cond do
...(1)>   1 + 1 == 4 -> "Never seen"
...(1)>   2 * 3 == 9 -> "Nope" 
...(1)>   1 + 2 == 3 -> "Shown"
...(1)> end
"Shown"

or if you prefer use elixirc to run the (example.ex) program below:

x = 3
cond do
   x == 1 -> IO.puts "It's 1!"
   x == 2 -> IO.puts "It's 2!"
   x == 3 -> IO.puts "It's 3!"
   true   -> IO.puts "I surrender."
end

CondClauseError

If no condition matches, CondClauseError is raised.

iex(4)> cond do
...(4)>   1 + 3 == 9 -> "Never"
...(4)> end
** (CondClauseError) no cond clause evaluated to a true value

Because of that you may want to add true to the as a final condition, which will always match.

iex(4)> cond do
...(4)>   3 > 1 -> "Never"
...(4)>   true -> "No maches found"
...(4)> end
"Never"

You may use else if clauses in many imperative languages. You can use this instead of nesting many if statements.

Try catch

Try-catch is used to catch values that are thrown. The try catch clause first tries to execute
the codeblock. Then if a message is thrown, it goes into the catch clause.

The concept of try-catch is not unique to Elixir, it’s available in many programming languages.

Try catch example

You can try this in the elixir interactive shell iex. Or if you prefer, add it to an elixir program.
Then we throw a value with throw(:hello).

try do
  throw(:hello)
catch
  message -> "Received #{message}."
end

This program outputs

"Received hello."

After clause

Elixir has the after clause. If a value is not caught, it will execute that clause.
In the example below a value is thrown, so it goes into the catch clause.

try do
  throw(:hello)
catch
  message -> "Received #{message}."
after
  IO.puts("I'm the after clause.")
end

If you do not throw a value, it jumps straight into the after clause:

try do
catch
  message -> "Received #{message}."
after
  IO.puts("After clause.")
end

In other programming languages that is the finally case;