Decided to try out converting a haskell prime number generator to Nix to test this
{ num }:
with import <nixpkgs/lib>;
rec {
filter = f: { head, tail }:
let newTail = filter f tail;
in if f head then { inherit head; tail = newTail; } else newTail;
unfoldr = f: b:
let a = f b;
in { head = a.elem; tail = unfoldr f a.next; };
primes = {
head = 2;
tail = filter
(isPrime primes)
(unfoldr (n: { elem = n; next = n + 2; }) 3);
};
isPrime = { head, tail }: n:
head * head > n || mod n head != 0 && isPrime tail n;
get = { head, tail }: n: if n == 0 then head else get tail (n - 1);
foo = get primes num;
bar = get primes num + get primes num;
}
$ time nix eval -f sleep.nix foo --arg num 20000
224743
real 0m1.901s
user 0m1.798s
sys 0m0.104s
$ time nix eval -f sleep.nix bar --arg num 20000
449486
real 0m1.907s
user 0m1.804s
sys 0m0.103s
Pretty much identical, so it looks like it is doing maximal laziness. I guess this is just disabled somehow for builtins.exec
?