Skip to content

Memory leak when using nested Seq.unfold to generate first 1000000 primes #14758

Description

@chav-n

For the purpose of learing F# I tried solving a typical programming exercise: write a program that prints all primes. To make it more challenging, I wrote an implementation where recursions/loops were replaced with two nested Seq.unfold usages.Then I modified it to print the nth prime. Here is a function that will print the nth prime after generating the first n primes:

let printAllPrimesSeq() =
  let tryFindPrimeDivisor primesL i =
    (primesL |> List.takeWhile(fun x -> x*x <= i) |> List.tryFind(fun x -> i % x = 0))
  let nextPrime primesL =
     let tryFindPrimeDivisor1 = tryFindPrimeDivisor (List.fold (fun acc elem -> elem::acc) [] primesL)
     fst(
       Seq.unfold
         (fun (i: int) -> Some(
           (i, tryFindPrimeDivisor1 i),
           (i + 2)))
         (primesL.Head + 2)
       |> Seq.find(fun x -> snd x = None))
  let allPrimes =
    Seq.unfold
      (fun (primes: int list) ->
        let i' = (nextPrime primes)
        Some(i', i'::primes))
      ([3])

  (*
  printf "2, 3, "
  for i in allPrimes do
    printf "%i, " i
   *)
  printf "Please give a number: "
  let n = int (System.Console.ReadLine())
  let prime =
    if n = 1 then 2
    elif n = 2 then 3
    else (allPrimes |> Seq.take(n - 2) |> Seq.last)
  printf "%i" prime

Requesting the 1000000th prime will send memory usage above 5GB in Windows 11 (only the *.exe file), half an hour later, running on 10th gen Core i5. The dotnet generated project is set to net7.0. Other programs running in the background: Chrome, Notepad++

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    Status
    Done

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions