45 lines
981 B
Haskell
45 lines
981 B
Haskell
import Data.List (elemIndex)
|
|
|
|
chao :: Eq a => [a] -> [a] -> Bool -> [a] -> [a]
|
|
chao _ _ _ [] = []
|
|
chao l r plain (x : xs) = maybe [] go (elemIndex x src)
|
|
where
|
|
(src, dst)
|
|
| plain = (l, r)
|
|
| otherwise = (r, l)
|
|
go n =
|
|
dst !! n :
|
|
chao
|
|
(shifted 1 14 (rotated n l))
|
|
((shifted 2 14 . shifted 0 26) (rotated n r))
|
|
plain
|
|
xs
|
|
|
|
rotated :: Int -> [a] -> [a]
|
|
rotated n = take . length <*> drop n . cycle
|
|
|
|
shifted :: Int -> Int -> [a] -> [a]
|
|
shifted src dst s = concat [x, rotated 1 y, b]
|
|
where
|
|
(a, b) = splitAt dst s
|
|
(x, y) = splitAt src a
|
|
|
|
encode, decode :: Bool
|
|
encode = False
|
|
decode = True
|
|
|
|
main :: IO ()
|
|
main = do
|
|
let chaoWheels =
|
|
chao
|
|
"HXUCZVAMDSLKPEFJRIGTWOBNYQ"
|
|
"PTLNBQDEOYSFAVZKGJRIHWXUMC"
|
|
plainText = "WELLDONEISBETTERTHANWELLSAID"
|
|
cipherText = chaoWheels encode plainText
|
|
mapM_
|
|
print
|
|
[ plainText,
|
|
cipherText,
|
|
chaoWheels decode cipherText
|
|
]
|