У меня есть следующие функции Haskell:
expM :: Integer -> Integer -> Integer -> Integer
expM x y = rem (x^y)
И
exMME :: Integer -> Integer -> Integer -> Integer
exMME b 0 m = 1
exMME b e m = exMME' b e m 1 0 where
exMME' b e m c e'
| e' < e = exMME' b e m ((b * c) `mod` m) (e'+1)
| otherwise = c
Я хочу использовать quickCheck для сравнения этих двух функций, чтобы я мог видеть, что они дают один и тот же ответ и какая из них самая быстрая.
Чтобы проверить, есть ли у них одинаковые ответы, я хочу, чтобы QuickCheck создавал случайные положительные целые числа за исключением 0. Итак, я создал Gen:
positives :: Gen Integer
positives =
do -- Pick an arbitrary integer:
x <- arbitrary
if (x == 0)
then return 1
else if (x < 0)
then return (-x)
else
return x
Это работает из командной строки (ghci), но у меня есть опора:
prop_CompareAnswerExMFM :: Integer -> Integer -> Integer -> Bool
prop_CompareAnswerExMFM b e m =exMFM b e m == exM b e m
И каждый раз, когда я вызываю это с помощью QuickCheck prop_CompareAnswerExMFM, это не соответствует моему поколению. Прочитав кое-что, я сказал, что мне нужно определить экземпляр:
instance Arbitrary Integer where
arbitrary = positives
Это не работает, потому что уже существует произвольный экземпляр Integer. Опять же, после некоторого поиска в Google я говорю, что стандартный способ решить эту проблему - использовать оболочку:
newtype Positives = Positives Integer
deriving (Eq, Ord, Show)
instance Arbitrary Positives where
arbitrary = positives
positives :: Gen Positives
positives =
do -- Pick an arbitrary integer:
x <- arbitrary
if (x == 0)
then return 1
else if (x < 0)
then return (-x)
else
return x
Но после игры я продолжаю получать ошибки, например, не могу решить это, Нет экземпляра для (Num Positives), возникающего из буквального «0» или Can't make a производный экземпляр «Num Positives».
Я думаю, что усложняю то, что хочу, но я просто не могу этого понять. Я надеюсь, что кто-нибудь сможет мне помочь или направить меня в правильном направлении.
Спасибо
quickcheck
: Положительно ... конечно, вы должны использовать это так:prop :: Positive -> Bool
, а затемprop (Positive n) = ...
(разбейте его с помощью сопоставления с образцом, чтобы получить само число!) - или используйтеgetPositive
внутри своей собственности, чтобы получить номер - person Random Dev   schedule 11.10.2015