I’m writing a bit of code to help me with some math stuff. I’m trying to implement the Miller test, not Miller-Rabin, and I need to make a list of a bunch of exponents. Here’s the code so far. It inserts the last result twice for some reason, and I don’t know why. I must not understand how the until function works.
import Math.NumberTheory.Powers
divides::Integer->Integer->Bool
divides x y = y `mod` x == 0
factorcarmichael::Integer->(Integer,Integer)
factorcarmichael n = until (\(_, s) -> not $ divides 2 s)
(\(r, s) -> (r+1, div s 2))
(0, n-1)
second::((Integer,Integer),[Integer])->[Integer]
second (x,xs) = xs
millerlist::Integer->Integer->[Integer]
millerlist a n = second $ until (\((r,s), xs) -> r<0)
(\((r,s), xs) -> ((r-1,s), (powerMod a ((2^r)*s) n):xs))
(factoredcarmichael, [])
where
factoredcarmichael = factorcarmichael n
Also, the millerlist function is a little kludgy. If someone can suggest an alternative, that would be nice.
The output I’m getting for
millerlist 8888 9746347772161
repeats the last element twice.
That is because
so the number appears twice in the list. But your list is one too long, I believe. I think you only want the remainder of
a^(2^k*s)modulonfor0 <= k < r.As for alternatives, is there a particular reason why you’re not using
Math.NumberTheory.Primes.isStrongFermatPP? If you’re only interested in the outcome, that’s less work coding.If you want to generate the list, what about
or