Skip to content

Instantly share code, notes, and snippets.

@relrod
Last active August 29, 2015 14:26
Show Gist options
  • Save relrod/9c9e6fb1f43f3ed1a06d to your computer and use it in GitHub Desktop.
Save relrod/9c9e6fb1f43f3ed1a06d to your computer and use it in GitHub Desktop.
A quick and hacky program I threw together fo taking the caesar-shift cipher of a string 25 times. Used for the MathFest Dash scavenger hunt.
{-# LANGUAGE OverloadedStrings #-}
import Data.Function (on)
import qualified Data.ByteString.Lazy.Char8 as B
import Crypto.Classical
import System.Environment
import qualified Data.Text.Lazy as T
import qualified Data.Text.Lazy.IO as T
import Data.Char (toLower, isAlpha)
import Data.List
cae :: String -> [T.Text]
cae s = map (\x -> T.pack $ map toLower $ B.unpack $ _caesar $ (decrypt x (B.pack s) :: Caesar B.ByteString)) [1..25]
wordsF :: IO [T.Text]
wordsF = T.lines <$> T.readFile "/usr/share/dict/words"
matchWords :: [T.Text] -> [T.Text] -> (T.Text, Int)
matchWords s words' =
let f = filter (\x -> [T.filter isAlpha x] `isInfixOf` words') s
in (T.unwords s, length f)
printNumbered :: Int -> T.Text -> Double -> IO ()
printNumbered n s conf =
T.putStrLn $ (T.pack . show $ n) `mappend` ".\t" `mappend` s `mappend`
"\t(confidence: ~" `mappend` (T.pack . take 5 . show $ (conf * 100))
`mappend` "%)"
main :: IO ()
main = do
encr <- fmap head getArgs
let strs = cae encr
w <- wordsF
putStrLn "In order of likelihood:"
let l = reverse . sortBy (compare `on` snd) $ map (\x -> matchWords (T.words x) w) strs
l' = zip [1..] l
maxConf = maximum $ map snd l
mapM_ (\(i, (str, confidence)) -> printNumbered i str (fromIntegral confidence / fromIntegral maxConf)) l'
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment