Write Vigenère cipher exercise
This commit is contained in:
parent
873ab82b19
commit
126064340b
64
16_vigenere.lua
Normal file
64
16_vigenere.lua
Normal file
@ -0,0 +1,64 @@
|
|||||||
|
-- The Vigenère cipher is a way to encrypt text, where a key is
|
||||||
|
-- repeated for the length of the plaintext and the alphabetical
|
||||||
|
-- position of the keyword letter determines the amount the letter of
|
||||||
|
-- the plaintext is shifted by. For example, for plaintext "FOO" and
|
||||||
|
-- key "BAR", the first letter of the cipher text would be G, the
|
||||||
|
-- result of shifting the letter F (first letter of the plaintext)
|
||||||
|
-- over by 1 (the zero-based alphabetical position of B, first letter
|
||||||
|
-- of the key).
|
||||||
|
--
|
||||||
|
-- Implement a function to encode a message with a given keyword. The
|
||||||
|
-- message should be converted to upper-case and any non-alphabetical
|
||||||
|
-- characters should be discarded.
|
||||||
|
--
|
||||||
|
-- Solution --------------------------------------------------------------------
|
||||||
|
local a_value = 65
|
||||||
|
|
||||||
|
function apply_shift(letter, shift)
|
||||||
|
local shifted = (letter - a_value + shift) % 26
|
||||||
|
return a_value + shifted
|
||||||
|
end
|
||||||
|
|
||||||
|
function vigenere_encode(plaintext, keyword)
|
||||||
|
local key = {}
|
||||||
|
for i = 1, #keyword do
|
||||||
|
local shift = string.byte(keyword, i) - a_value
|
||||||
|
table.insert(key, shift)
|
||||||
|
end
|
||||||
|
|
||||||
|
plaintext = string.gsub(string.upper(plaintext), "%A+", "")
|
||||||
|
ciphertext = ""
|
||||||
|
for i = 1, #plaintext do
|
||||||
|
local letter = string.byte(plaintext, i)
|
||||||
|
local shift = key[(i - 1) % #key + 1]
|
||||||
|
local shifted = apply_shift(letter, shift)
|
||||||
|
ciphertext = ciphertext .. string.char(shifted)
|
||||||
|
end
|
||||||
|
|
||||||
|
return ciphertext
|
||||||
|
end
|
||||||
|
|
||||||
|
-- Tests -----------------------------------------------------------------------
|
||||||
|
|
||||||
|
local luaunit = require("luaunit.luaunit")
|
||||||
|
|
||||||
|
function test_encoding_of_foo_with_key_BAR()
|
||||||
|
luaunit.assertEquals(vigenere_encode("FOO", "BAR"), "GOF")
|
||||||
|
end
|
||||||
|
|
||||||
|
function test_encoding_of_the_quick_brown_fox_with_key_JUMPSOVER()
|
||||||
|
local plaintext = "The quick brown fox"
|
||||||
|
local key = "JUMPSOVER"
|
||||||
|
local expected = "CBQFMWXOSAIICXCS"
|
||||||
|
luaunit.assertEquals(vigenere_encode(plaintext, key), expected)
|
||||||
|
end
|
||||||
|
|
||||||
|
function test_encoding_longer_phrase_with_key_LEAR()
|
||||||
|
local plaintext =
|
||||||
|
"They dined on mince and slices of quince, which they ate with a runcible spoon."
|
||||||
|
local key = "LEAR"
|
||||||
|
local expected = "ELEPOMNVOSNDTRCVLRDJWMCVDSFHFMNTPAHZNLTYPCAKPAIKSERLYGISWISGZSN"
|
||||||
|
luaunit.assertEquals(vigenere_encode(plaintext, key), expected)
|
||||||
|
end
|
||||||
|
|
||||||
|
os.exit(luaunit.LuaUnit.run())
|
Loading…
x
Reference in New Issue
Block a user