The Goldbach Conjecture is one of the oldest unsolved problems in mathematics. It states that every even integer greater than 2 can be expressed as the sum of two prime numbers.

While no formal proof has been found, the conjecture has been verified by computers for very large numbers. In this post, we’ll explore how to express this idea recursively in Haskell — using an elegant search through the space of prime pairs.

1. Restating the problem

For any even number x > 2, find two primes p1 and p2 such that:

p1 + p2 = x

For example:

The challenge is to find such a pair efficiently — and recursion provides a natural way to iterate through potential candidates.

2. The full implementation

Let’s look at my implementation of the Goldbach function in Haskell:

goldbach :: Int -> (Int, Int)
goldbach x = subGoldbach x 1 (subGoldbachDesc x)

subGoldbach :: Int -> Int -> Int -> (Int, Int)
subGoldbach x v1 v2 = 
    let (newv1, newv2) = updateInterval v1 v2
    in if (v1 + v2) == x
       then (v1, v2)
       else subGoldbach x newv1 newv2

updateInterval :: Int -> Int -> (Int, Int)
updateInterval v1 v2
    | v1 == v2 = (1, subGoldbachDesc v2)
    | otherwise = (subGoldbachAsc (v1 + 1) v2, v2)

subGoldbachDesc :: Int -> Int
subGoldbachDesc 1 = 1
subGoldbachDesc x
    | isPrime x = x
    | otherwise = subGoldbachDesc (x - 1)

subGoldbachAsc :: Int -> Int -> Int
subGoldbachAsc x cmp
    | x == cmp = cmp
    | isPrime x = x
    | otherwise = subGoldbachAsc (x + 1) cmp

Note that the function isPrime is assumed to exist — it checks if a number is prime. The rest of the program is a clean, recursive search over possible prime pairs.

3. How it works

The entry point goldbach begins with two values:

Then, subGoldbach checks whether the current pair (v1, v2) satisfies the Goldbach condition:

The function updateInterval moves our search boundaries:

4. Descending and ascending through primes

Two helper functions are at the heart of the search: subGoldbachDesc and subGoldbachAsc.

subGoldbachDesc finds the largest prime less than or equal to x:

subGoldbachDesc :: Int -> Int
subGoldbachDesc 1 = 1
subGoldbachDesc x
    | isPrime x = x
    | otherwise = subGoldbachDesc (x - 1)

Meanwhile, subGoldbachAsc finds the next prime greater than or equal to a given number, but not exceeding a comparison limit:

subGoldbachAsc :: Int -> Int -> Int
subGoldbachAsc x cmp
    | x == cmp = cmp
    | isPrime x = x
    | otherwise = subGoldbachAsc (x + 1) cmp

These two recursive helpers define the upward and downward motion through the prime number space, continuously adjusting our pair candidates until a valid combination is found.

5. Step-by-step intuition

Think of the algorithm as two pointers moving inside a shrinking window:

At each recursive step:

  1. Check if v1 + v2 == x.
  2. If not, move v1 upward to the next prime.
  3. If v1 catches up to v2, move v2 downward to the next smaller prime and restart v1.

Eventually, recursion guarantees that all possible pairs of primes are checked, and the first valid one is returned as the Goldbach decomposition.

6. Example

Let’s run an example:

main = print (goldbach 28)

Suppose subGoldbachDesc 28 gives us v2 = 23. Then recursion begins:

The function returns (5, 23), one valid Goldbach pair for 28.

7. Why recursion fits perfectly here

The structure of the Goldbach problem is naturally recursive: each step depends only on a smaller subproblem — finding the next suitable primes.

It’s a perfect example of functional recursion as an elegant search mechanism — no mutable state, no explicit loops, just pure logical flow.

8. Wrap-up

The Goldbach Conjecture may remain unproven, but in Haskell, we can express its logic clearly and functionally.

Whether or not Goldbach is ever proven true, one thing is certain: recursion in Haskell provides one of the cleanest ways to think like a mathematician in code.



Comment


Not that much comments



Next
Before