簡體   English   中英

Haskell中的實例聲明

[英]Instance declaration in Haskell

我有這兩個功能:

primes = sieve [2..] 
    where
        sieve (p:xs) = p : sieve [x|x <- xs, x `mod` p > 0]
isPrime number = number /= 1 && null [x | x <- takeWhile (\x -> x < (ceiling . sqrt) number) primes, mod number x == 0]

問題是,當我嘗試加載包含這些函數的模塊時,我看到以下錯誤消息:

[2 of 2] Compiling Main             ( euler37.hs, interpreted )

euler37.hs:6:70:
No instance for (RealFrac Int)
  arising from a use of `ceiling'
Possible fix: add an instance declaration for (RealFrac Int)
In the first argument of `(.)', namely `ceiling'
In the expression: ceiling . sqrt
In the second argument of `(<)', namely `(ceiling . sqrt) number'

euler37.hs:6:80:
No instance for (Floating Int)
  arising from a use of `sqrt'
Possible fix: add an instance declaration for (Floating Int)
In the second argument of `(.)', namely `sqrt'
In the expression: ceiling . sqrt
In the second argument of `(<)', namely `(ceiling . sqrt) number'

我真的無法理解是什么問題,因為當我試圖從一段代碼中創建一個小函數時,據我所知,這會導致這些錯誤,就在ghci中,就像讓f number x = x < (ceiling.sqrt)數字我沒有看到任何錯誤消息。

問題是primes是一個Integers列表(由於你使用了mod ),但是sqrt是在浮點數上運行的。 如果你做x < (ceiling . sqrt . fromIntegral) number ,那么它將正常工作。 fromIntegral只是將整數轉換為任何其他數字類型:

fromIntegral :: (Integral a, Num b) => a -> b

在這種情況下,由於您沒有指定要轉換的任何特定浮點類型,因此默認使用Double值來計算平方根。 您可以通過將fromIntegral更改為類似(fromIntegral :: Integer -> Float)來指定其他類型。

您在GHCi中沒有看到此錯誤的原因是因為您的條件很好; 它只適用於你在這里使用的不同類型。 僅僅驗證一段代碼在隔離中是否正確是不夠的; 為了通過類型檢查器,它也必須在上下文中有意義。

您可能需要考慮使用整數平方根算法來提高准確性。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM