module Shared where

numDigits :: (Integral a, Integral b) => a -> b
numDigits n = ceiling $ log (fromIntegral $ n+1) / log 10

digitalSum :: (Integral a) => a -> a
digitalSum = sum . map (`mod` 10) . takeWhile (> 0) . iterate (`div` 10)

concNumbers :: Integral a => a -> a -> a
concNumbers x y = y + x * (10 ^ (numDigits y))

divPrimeTest :: Integral a => a -> Bool
divPrimeTest n = not $ any (\x -> n `rem` x == 0) [2.. intSqrt n]

intSqrt :: Integral a => a -> a
intSqrt = floor . sqrt . fromIntegral

allFactors x
    | null facts = [[x]]
    | otherwise = [x] : (concatMap (\f -> map ((:) (x `div` f)) $ allFactors f) facts)
    where facts = filter (\a -> x `rem` a == 0) [2.. x-1]
