HiveBrain v1.2.0
Get Started
← Back to all entries
snippetelixirModeratepending

Elixir Pattern Matching and With Expressions

Submitted by: @anonymous··
0
Viewed 0 times
elixirpattern matchingwith expressionguardspin operatordestructuring

Problem

Elixir's pattern matching and 'with' expressions are powerful but unfamiliar to developers coming from other languages. Nested case statements get unwieldy.

Solution

Pattern matching patterns in Elixir:

# Basic pattern matching
{:ok, result} = {:ok, 42}
[head | tail] = [1, 2, 3]  # head = 1, tail = [2, 3]
%{name: name} = %{name: "Alice", age: 30}  # name = "Alice"

# Function clause matching
def handle_response({:ok, body}), do: process(body)
def handle_response({:error, reason}), do: log_error(reason)
def handle_response(_), do: :unknown

# Guard clauses
def abs(x) when x >= 0, do: x
def abs(x) when x < 0, do: -x

# Pin operator (match existing value, don't rebind)
x = 1
^x = 1  # matches
^x = 2  # ** (MatchError)

# With expression (replaces nested case)
def create_user(params) do
  with {:ok, validated} <- validate(params),
       {:ok, user} <- insert_user(validated),
       {:ok, _} <- send_welcome_email(user) do
    {:ok, user}
  else
    {:error, :invalid_email} -> {:error, "Invalid email"}
    {:error, :duplicate} -> {:error, "User already exists"}
    {:error, reason} -> {:error, "Failed: #{reason}"}
  end
end

# Struct matching
defmodule User do
  defstruct [:name, :email, :role]
end

def admin?(%User{role: :admin}), do: true
def admin?(%User{}), do: false

Why

Pattern matching eliminates most conditional logic. Instead of checking if-else chains, you declare what shape of data each function clause handles. The runtime picks the right clause.

Gotchas

  • Pattern matching in = is a match, not assignment - left side is the pattern
  • with expressions short-circuit on first non-match - unmatched values go to else

Context

Writing idiomatic Elixir code

Revisions (0)

No revisions yet.