Functions in Clojure

Functions are central in Clojure. We’ll learn about functions with a few different examples.

(ns functions-example
  (:require [clojure.core :refer [println]]))

;; Here's a function that takes two numbers and returns
;; their sum.
(defn plus [a b]
  (+ a b))

;; In Clojure, functions can take multiple arguments without
;; explicitly declaring their types.
(defn plus-plus [a b c]
  (+ a b c))

(defn -main []
  ;; Call a function just as you'd expect, with
  ;; (function-name args).
  (let [res (plus 1 2)]
    (println "1+2 =" res))

  (let [res (plus-plus 1 2 3)]
    (println "1+2+3 =" res)))

To run the program, you can use the Clojure CLI or REPL:

$ clj -M functions_example.clj
1+2 = 3
1+2+3 = 6

Let’s break down the key points:

  1. In Clojure, functions are defined using the defn macro.
  2. Function arguments are specified in a vector after the function name.
  3. The function body is the expression(s) after the argument vector.
  4. Clojure doesn’t require explicit type declarations for function arguments or return values.
  5. The last expression in a function is automatically returned.
  6. Function calls are written as (function-name arg1 arg2 ...).
  7. Local bindings are created using the let special form.

Clojure’s functional nature allows for concise and expressive function definitions. The language emphasizes immutability and encourages a functional programming style.

There are several other features to Clojure functions. One is multiple return values, which we’ll look at next.