Haskell数字类型沮丧

时间:2012-03-25 18:57:40

标签: haskell numbers

我遇到了一个简单的Haskell程序问题。它应该将数字n-1分解为形式(2 ^ r)s,其中n是Carmichael数。这与我的问题并不完全相关,但它是以下一系列功能的目的。

divides::Int->Int->Bool
divides x y = not $ y `mod` x == 0

carmichaeltwos::Int->Int
carmichaeltwos n
    | not $ divides 2 n =0
    | otherwise = (+ 1) $ carmichaeltwos (n/2)

carmichaelodd::Int->Int
carmichaelodd n
    | not $ divides 2 n = n
    | otherwise = carmichaelodd (n/2)

factorcarmichael::Int->(Int, Int)
factorcarmichael n = (r, s)
    where
        nminus = n-1
        r = carmichaeltwos nminus
        s = carmichaelodd nminus

当我尝试将其加载到GHCi中时,Haskell吐了出来:

No instance for (Fractional Int)
  arising from a use of `/'
Possible fix: add an instance declaration for (Fractional Int)
In the first argument of `carmichaelodd', namely `(n / 2)'
In the expression: carmichaelodd (n / 2)
In an equation for `carmichaelodd':
    carmichaelodd n
      | not $ divides 2 n = n
      | otherwise = carmichaelodd (n / 2)

我知道函数/有类型(/):((分数a)=> a-> a-> a,但是我没有看到如何修复我的程序以使其工作得很好。

另外,我意识到我基本上在factorcarmichael函数中计算了两次相同的东西。我想不出任何简单的方法可以在一次通过中计算数字并获得我想要的元组作为答案。

1 个答案:

答案 0 :(得分:5)

如果您知道(如果在此情况下)被除数可被除数整除,则要分割两个Int,请使用divquot函数,即{{1} }或div n 2。 (quot n 2div仅在“真实”商不是整数时对负操作数的处理方面有所不同。)

另外,为什么要将quot定义为divides?除非您使用“divides”的非标准含义,否则您应该只使用not $ mod y x == 0 - mod y x == 0除以x iff y modulo { {1}}为零。

至于合并yx,请尝试使用carmichaeltwos函数:

carmichaelodd