Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Lazy List of Prime Numbers

How would one implement a list of prime numbers in Haskell so that they could be retrieved lazily?

I am new to Haskell, and would like to learn about practical uses of the lazy evaluation functionality.

like image 249
Mantas Vidutis Avatar asked Aug 29 '10 20:08

Mantas Vidutis


People also ask

What are the first 1000 prime numbers?

2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97, 101, 103, 107, 109, 113, 127, 131, 137, 139, 149, 151, 157, 163, 167, 173, 179, 181, 191, 193, 197, 199, 211, 223, 227, 229, 233, 239, 241, 251, 257, 263, 269, 271, 277, 281, 283, 293.

Why 1 is not a prime number?

1 can only be divided by one number, 1 itself, so with this definition 1 is not a prime number. It is important to remember that mathematical definitions develop and evolve. Throughout history, many mathematicians considered 1 to be a prime number although that is not now a commonly held view.

Are all numbers ending in 7 prime?

Apart from 2 and 5, all prime numbers have to end in 1, 3, 7 or 9 so that they can't be divided by 2 or 5.

How many prime numbers are there between 1 and 1000?

There are a total of 168 prime numbers in the list of prime numbers from 1 to 1000.


2 Answers

Here's a short Haskell function that enumerates primes from Literate Programs:

primes :: [Integer] primes = sieve [2..]   where     sieve (p:xs) = p : sieve [x|x <- xs, x `mod` p > 0] 

Apparently, this is not the Sieve of Eratosthenes (thanks, Landei). I think it's still an instructive example that shows you can write very elegant, short code in Haskell and that shows how the choice of the wrong data structure can badly hurt efficiency.

like image 82
Niki Avatar answered Sep 20 '22 16:09

Niki


There are a number of solutions for lazy generation of prime sequences right in the haskell wiki. The first and simplest is the Postponed Turner sieve: (old revision ... NB)

primes :: [Integer] primes = 2: 3: sieve (tail primes) [5,7..]  where    sieve (p:ps) xs = h ++ sieve ps [x | x <- t, x `rem` p /= 0]                                   -- or:  filter ((/=0).(`rem`p)) t                   where (h,~(_:t)) = span (< p*p) xs 
like image 24
sleepynate Avatar answered Sep 21 '22 16:09

sleepynate