patternpythonMinor
Simplifying working Caesar cipher
Viewed 0 times
caesarworkingsimplifyingcipher
Problem
I'm learning Python 3 at the moment, so to test the skills I've learned, I am trying the puzzles at Python Challenge.
I've created some code to solve the 2nd puzzle here. it works, but I think that the way I've done it is very convoluted. Any suggestions on how to solve the puzzle in a simpler way?
(The code basically needs to substitute each letter in a message to the letter 2 spaces to the right of it, such as E->G.)
I've created some code to solve the 2nd puzzle here. it works, but I think that the way I've done it is very convoluted. Any suggestions on how to solve the puzzle in a simpler way?
(The code basically needs to substitute each letter in a message to the letter 2 spaces to the right of it, such as E->G.)
import string
alphabet = string.ascii_lowercase
letter=0
replaceLetter = 2
times=1
message = input()
newMessage=''
while times < 26:
newMessage = message.replace(alphabet[letter], str(replaceLetter)+',')
message = newMessage
letter = letter + 1
replaceLetter = replaceLetter + 1
time = times + 1
if letter == 26:
times = 0
break
newMessage = message.replace('26'+',', 'a')
message = newMessage
newMessage = message.replace('27'+',', 'b')
message = newMessage
number = 25
message = newMessage
while times < 26:
newMessage = message.replace(str(number)+',', str(alphabet[number]))
message = newMessage
letter = letter + 1
number = number - 1
time = times + 1
if number == -1:
times = 0
break
print(newMessage)Solution
I would define a shift function that shifted the letters like so:
Then, to translate a message:
Alternatively, combine Mark Tolonen's maketrans suggestion with g.d.d's deque suggestion to get:
Then, later in the code:
This second method only works for lowercase letters, but you can always create two separate translation tables -- one for uppercase letters and another for lowercase letters -- to account for case.
Offtopic note: sometimes I wish Python had Smalltalk-like cascaded message sends. Ah well, one can dream.
from string import whitespace, punctuation
def shift(c, shift_by = 2):
if c in whitespace + punctuation: return c
upper_ord, lower_ord, c_ord = ord('A'), ord('a'), ord(c)
c_rel = (c_ord - lower_ord) if c_ord >= lower_ord else (c_ord - upper_ord)
offset = lower_ord if c_ord >= lower_ord else upper_ord
return chr(offset + (c_rel + shift_by) % 26)Then, to translate a message:
msg = 'a quick brown fox jumped over the lazy dog'
encoded_msg = ''.join(shift(l) for l in msg)Alternatively, combine Mark Tolonen's maketrans suggestion with g.d.d's deque suggestion to get:
import string
from collections import deque
alphabet = string.ascii_lowercase
alphabet_deque = deque(alphabet)
alphabet_deque.rotate(-2)
rotated_alphabet = ''.join(alphabet_deque)
tbl = string.maketrans(alphabet, rotated_alphabet)Then, later in the code:
msg = 'a quick brown fox jumped over the lazy dog'
encoded_msg = string.translate(msg, tbl)This second method only works for lowercase letters, but you can always create two separate translation tables -- one for uppercase letters and another for lowercase letters -- to account for case.
Offtopic note: sometimes I wish Python had Smalltalk-like cascaded message sends. Ah well, one can dream.
Code Snippets
from string import whitespace, punctuation
def shift(c, shift_by = 2):
if c in whitespace + punctuation: return c
upper_ord, lower_ord, c_ord = ord('A'), ord('a'), ord(c)
c_rel = (c_ord - lower_ord) if c_ord >= lower_ord else (c_ord - upper_ord)
offset = lower_ord if c_ord >= lower_ord else upper_ord
return chr(offset + (c_rel + shift_by) % 26)msg = 'a quick brown fox jumped over the lazy dog'
encoded_msg = ''.join(shift(l) for l in msg)import string
from collections import deque
alphabet = string.ascii_lowercase
alphabet_deque = deque(alphabet)
alphabet_deque.rotate(-2)
rotated_alphabet = ''.join(alphabet_deque)
tbl = string.maketrans(alphabet, rotated_alphabet)msg = 'a quick brown fox jumped over the lazy dog'
encoded_msg = string.translate(msg, tbl)Context
StackExchange Code Review Q#6493, answer score: 3
Revisions (0)
No revisions yet.