Skip to content

Instantly share code, notes, and snippets.

@amalex5
Last active September 26, 2016 02:58
Show Gist options
  • Save amalex5/5c01244e6f5c46828cd768084cd61c14 to your computer and use it in GitHub Desktop.
Save amalex5/5c01244e6f5c46828cd768084cd61c14 to your computer and use it in GitHub Desktop.
-- can we have a triply palindromic bill???
-- i.e., a bill where the subtotal, the tip, and the total are all numeric palindromes?
-- (note that we're doing all these calculations in cents)
isPalindrome :: Eq a => [a] -> Bool
isPalindrome x = x == reverse x
numToDigits n = map (\x -> read [x] :: Int) (show n)
numIsPalindrome :: Show a => a -> Bool
numIsPalindrome x = isPalindrome (numToDigits x)
stingyTip = 0.1 -- 10%
generousTip = 0.3 -- 30%
reasonableTips :: Integral a => a -> [Int]
reasonableTips x = map (\z -> fromIntegral z :: Int) (map round [ n * stingyTip .. n * generousTip])
where n = fromIntegral x
-- stupid number casting crap
triplePalindromes n = [ (sub, tip, tot) | sub <- [1..n],
numIsPalindrome sub,
tip <- reasonableTips sub,
numIsPalindrome tip,
tot <- [sub + tip],
numIsPalindrome tot
]
-- there are tons and tons!
-- e.g., for bills below $100, and tips between 10 and 30%, we have:
-- length (triplePalindromes 10000)
-- > 488
showCurrency x = "$" ++ show (x `div` 100) ++ "." ++ if (cents < 10) then ("0" ++ show cents) else (show cents)
where cents = x `mod` 100
showTriplePalindrome (sub,tip,tot) = "subtotal: " ++ showCurrency sub ++
"; tip: " ++ showCurrency tip ++
"; total: " ++ showCurrency tot
printTriplePalindromesBelowN n = mapM (putStrLn . showTriplePalindrome) (triplePalindromes n)
-- handy reference list:
-- printTriplePalindromesBelowN 10000
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment