我正在研究OCaml中的素數分解的實現。我不是一個功能程序員;以下是我的代碼。素數分解在prime_part函數中遞歸地發生。 primes
是從0到num的素數列表。這樣做的目的是,我可以輸入prime_part進入OCaml的解釋,並把它吐了出來,當n = 20,K = 1For循環遍歷遞歸調用Ocaml
2 + 3 + 7
5 + 7
我適應is_prime
和all_primes
從OCaml的教程。將需要調用all_primes
以在調用prime_part
之前生成最多爲b
的質數列表。
(* adapted from http://www.ocaml.org/learn/tutorials/99problems.html *)
let is_prime n =
let n = abs n in
let rec is_not_divisor d =
d * d > n || (n mod d <> 0 && is_not_divisor (d+1)) in
n <> 1 && is_not_divisor 2;;
let rec all_primes a b =
if a > b then [] else
let rest = all_primes (a + 1) b in
if is_prime a then a :: rest else rest;;
let f elem =
Printf.printf "%d + " elem
let rec prime_part n k lst primes =
let h elem =
if elem > k then
append_item lst elem;
prime_part (n-elem) elem lst primes in
if n == 0 then begin
List.iter f lst;
Printf.printf "\n";
()
end
else
if n <= k then
()
else
List.iter h primes;
();;
let main num =
prime_part num 1 [] (all_primes 2 num)
我很大程度上與for循環的隱遁性質混淆。我看到List.ittr
是OCaml的方式,但是如果我爲List.ittr
定義了另一個函數,我將無法訪問我的變量。我需要訪問這些變量遞歸調用prime_part。什麼是更好的方式來做到這一點?
我可以在Ruby中表達我想用OCaml完成的事情。 N =任意數,k = 1,LST = [] =素數質數0列表到n
def prime_part_constructive(n, k, lst, primes)
if n == 0
print(lst.join(' + '))
puts()
end
if n <= k
return
end
primes.each{ |i|
next if i <= k
prime_part_constructive(n - i, i, lst+[i], primes)
}
end
我已編輯原始帖子中的OCaml代碼以反映您的建議更改。當我將它放入OCaml解釋器時,它正在轟炸函數h,因爲它無法訪問'lst'。它給了我一個'Unbound value lst'錯誤。任何想法爲什麼這可能是? – technogeek1995
你的函數'h'沒有被定義爲嵌套函數。如果你想要訪問'lst',你需要在* prime_part_constructive裏面定義*。 –
我把它移到了函數中(見上)。然而,口譯員說它找不到'h'。那是因爲我在使用它之前引用了它?如果是這樣,我怎樣才能在不破壞prime_part函數定義的情況下改變它。 – technogeek1995