Run this notebook

Use Livebook to open this notebook and explore new ideas.

It is easy to get started, on your machine or the cloud.

Click below to open and run it in your Livebook at .

(or change your Livebook location)

# Loops You can iterate over lists, tuples, keyword lists, and maps in a few different ways. Here are the most common ones: ## The `for/1` Comprehension ```elixir # You can iterate over a range ascending result = for idx <- 1..10//1, do: idx IO.inspect(result, label: "range - asc") # Or descending. Note the step of -2. # If you don't set the step, the loop will stop after the first element. result = for idx <- 10..1//-2, do: idx IO.inspect(result, label: "range - desc") # You can iterate through a list of elements result = for el <- ["Peter", 32, 190.47, :active], do: el IO.inspect(result, label: "elements") # Or you can have a nested for-loop result = for x <- [1, 2], y <- [4, 5], do: [x: x, y: y] IO.inspect(result, label: "nested") ``` <!-- livebook:{"output":true} --> ``` range - asc: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10] range - desc: [10, 8, 6, 4, 2] elements: ["Peter", 32, 190.47, :active] nested: [[x: 1, y: 4], [x: 1, y: 5], [x: 2, y: 4], [x: 2, y: 5]] ``` ## `Enum` helpers You will mostly use the `Enum` helper functions to iterate and modify collections. Here are the most used ones: ```elixir # Apply a function to every element and return the result. Enum.map([1, 2, 3], fn x -> x * 2 end) # => [2, 4, 6] # Apply a function, but ignore the result. Enum.each([1, 2, 3], fn x -> x * 2 end) # => :ok # Apply a function and add the result to an accumulator. Enum.reduce([1, 2, 3], 0, fn x, acc -> acc + x end) # => 6 # Only keep the elements for which the function evaluates to truthy and filter out the rest. Enum.filter([1, 2, 3], fn x -> x == 2 end) # => [2] # Reject/remove an element if the function evaluates to truthy. Enum.reject([1, 2, 3], fn x -> x == 2 end) # => [1, 3] ``` ## Recursive Functions A common pattern in functional programming is to have recursive loops using function clauses. Elixir uses [tail call optimisation](https://en.wikipedia.org/wiki/Tail_call) to keep the memory overhead low and to avoid stack overflows. ```elixir defmodule RunElixir.Loop do def loop(collection, fun), do: do_loop(collection, [], fun) # Applies an anonymous function to each element and returns the result as list. defp do_loop([], result, _fun), do: Enum.reverse(result) defp do_loop([value | rest], result, fun), do: do_loop(rest, [fun.(value) | result], fun) end RunElixir.Loop.loop([1, 2, 3], &(&1 * 2)) # => [2, 4, 6] ``` Our `loop/2` function executes the `do_loop/3` private function which calls itself recursively until it has traveresed the entire list. With every call, the second clause of `do_loop/3` removes one element from the list, applies the anonymous function to it, and adds the result to the results list. When the list of elements is exhausted, the first `do_loop/3` clause matches. It reverses the results and returns them.
See source

Have you already installed Livebook?

If you already installed Livebook, you can configure the default Livebook location where you want to open notebooks.
Livebook up Checking status We can't reach this Livebook (but we saved your preference anyway)
Run notebook

Not yet? Install Livebook in just a minute

Livebook is open source, free, and ready to run anywhere.

Run on your machine

with Livebook Desktop

Run in the cloud

on select platforms

To run on Linux, Docker, embedded devices, or Elixir’s Mix, check our README.

PLATINUM SPONSORS
SPONSORS
Code navigation with go to definition of modules and functions Read More ×