2014-11-02 61 views
0

我在使用F#中的素數檢查器時遇到了一些問題。它似乎沒有給出正確的結果,所以我猜我已經搞砸了邏輯的某處,但我不知道在哪裏。這個實現是一個簡單的暴力破解,所以邏輯並不複雜,我之前實現了使用for循環的類似解決方案。素數檢查

let rec isPrime iterator (n : int) = 
          match iterator with 
          | 1 -> isPrime (iterator + 1) n 
          | a when a = n -> isPrime (iterator + 1) n 
          | _ -> match n % iterator = 0 with 
            | true -> false 
            | false -> isPrime (iterator + 1) n 
+1

你可以充實你的問題來解釋你最初如何調用isPrime(即迭代器的初始值是什麼),並給出一個錯誤結果的例子。另外,你寫的代碼如何返回「真」? – 2014-11-02 16:09:55

+0

第二種情況應該評估爲「真」,而不是進一步遞歸..這是錯誤,感謝幫助我找到它! – 2014-11-02 16:12:27

回答

3

正如你已經在評論想通了,問題是,功能應該終止,並說true當迭代器達到n。實際上,通過迭代到n或至少n/2的平方根,可以使其更快,因爲到達n/2時,您知道這將是一個主要因素。

這樣的邏輯似乎是更容易使用if而不是match寫的 - 儘管你可以通過固定的情況下match輕鬆地修復它,我可能會寫類似:

let rec isPrime iterator (n : int) = 
    if iterator = n/2 then true 
    elif iterator = 1 then isPrime (iterator + 1) n 
    elif n % iterator = 0 then false 
    else isPrime (iterator + 1) n 

而且,你可能不希望將iterator參數暴露給用戶 - 您可以編寫使用嵌套函數,它們調用開始iterator = 2循環中的代碼(然後你不需要iterator = 1情況下,在所有):

let isPrime (n : int) = 
    let rec loop iterator = 
    if iterator = n/2 then true 
    elif n % iterator = 0 then false 
    else loop (iterator + 1) 
    loop 2 
+0

哦,嵌套的遞歸函數,這只是天才!我正在尋找一種在F#中實現可選參數的方法來實現同樣的功能,但嵌套遞歸更聰明!我已經避免使用'if'語句的原因是我讀到使用模式匹配的使用在F#中更具慣用性,但是您可以告訴我對F#完全陌生,所以我可能誤讀或誤解了:) 。 – 2014-11-02 18:13:55