1
x = input('Please Enter a Sentence: ')
y = input('Please Enter a Number: ')
y = int(y)
g = list(x)
j = ['a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z']
limit = 25
for e in g:
    q = j.index(e)
    if (q+y) > 25:   
        oman = (q+y) % 26
        newg = j[oman]
        print(newg, end="")
    elif (q+y) <= 25:
        newg = j[q+y]
        print(newg, end="")

I have to write a Caesar cipher for homework in python. (A caesar cipher shifts letters in phrase in order to decipher something.)

My program is supposed to take a sentence as and a number as input and shift each letter in the sentence by the input number. It works for phrases with no spaces, but I need it to work with spaces. Also, the program does not need to account for punctuation.

If anyone could give me some pointers on how to do this that would be very helpful.

I tried putting a space item in the alphabet variable but then the shift is off.

Martijn Pieters
  • 1,048,767
  • 296
  • 4,058
  • 3,343
user3046358
  • 35
  • 1
  • 2
  • 5
  • 3
    There are *thousands* of Cesar cipher questions here on Stack Overflow. None of those helped you with your problem? – Martijn Pieters Nov 28 '13 at 15:07
  • `j.index(' ')` would throw an exception; do you already know how to handle exceptions? You could catch the exception here and just print the character without translation. – Martijn Pieters Nov 28 '13 at 15:08
  • The only characters that you want to shift in the original sentence are alphabetic characters, correct? – Tim Pierce Nov 28 '13 at 15:11
  • How about "if e == ' ':" and then just continue? – Benjamin Maurer Nov 28 '13 at 15:43
  • You know, you don't need to check for the size of `q+y` if you always use `(q+y) % 26` in the index for `j`. So always just `newg = j[(q+y) % 26]` – Gustav Bertram Nov 28 '13 at 17:57
  • related: [Caesar Cipher Function in Python](http://stackoverflow.com/q/8886947/4279) -- the accepted answer works with spaces as is (it leaves them along). – jfs Feb 23 '15 at 12:51

4 Answers4

0

you can do like this

def Cesar(input_string,key):
    new_string=""
    for i in range(len(input_string)):
       if input_string[i].isalpha():
           curr_char=input_string[i].lower()
           #do your shifting to curr_char with key and append to a new string.
       elif input_string[i]==' ':
           new_string+=' '
    return new_string

As simple as that.

xor
  • 2,668
  • 2
  • 28
  • 42
0

You've pretty much conceived an algorithm for actually using the Caser key and encrypting a a message so I'll just mention how to ensure the program doesn't leave out a space and ignores punctuation as you asked.

 encrypt=str(input("Enter a message"))
 b=""
    for i in encrypt:
     if i==chr(32):
         b+=i
     #32 is the ASCII number for a space(" "), chr is a function which converts a character to its ASCII number
     #after carry on with the actual algorithm to encrypt letters

To ignore the punctuation, you'll probably need to do something like this:

if i in ("a","b","c","d","e","f","g","h","i","j","k","l","m","n","o","p","q","r","s","t","u","v","w","x","y","z"):

after the above, then carry out your execution of the code, that way the program will only deal with letters from a-z and nothing else.

83457
  • 203
  • 1
  • 11
0

I changed the code a bit, made it more general, and I tried to pick good descriptive names for the variables. You can now use a different list for ceasar - anything that is not in it will go through exactly the same.

On a related note, if you like cryptography, you can read the NSA's old cryptanalysis manuals.

There's a lot of interesting information about ciphers in there, and the information about letter frequency analysis would allow you write a program that breaks a Ceasar cipher without having to try all 25 shifts first!

sentence = input('Please Enter a Sentence: ')
number   = input('Please Enter a Number: ')

shift   = int(number)
letters = list(sentence)
cipher  = '' 

ceasar = ['a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x','y','z']

for letter in letters:
    if letter in ceasar:
        oldindex = ceasar.index(letter)
        newindex = (oldindex + shift) % len(ceasar)
        newletter = ceasar[newindex]
    else:
        newletter = letter

    print(letter, end="")
    cipher += newletter
Gustav Bertram
  • 14,591
  • 3
  • 40
  • 65
0

In case you don't want to store a list with the alphabet... (also handling Spanish chars)

def cesar(text, key):
    if key == 0:
        return text
    else:
        text = text.replace("á", chr(97)).replace("é", "e").replace("í", "i").replace("ó", "o").replace("ú", "u")\
        .replace("Á", "A").replace("É", "E").replace("Í", "I").replace("Ó", "O").replace("Ú", "U")\
        .replace("ñ", "n").replace("Ñ", "N")
        cipher = ""
        for x in range(len(text)):
            if text[x].isalpha():  # only shifting letters
                if text[x].islower():  # lowercase
                    cipher += chr((ord(text[x]) - 97 + key) % 26 + 97)
                else:  # uppercase
                    cipher += chr((ord(text[x]) - 65 + key) % 26 + 65)
            else:
                cipher += text[x]
        return cipher

The function ord(char) gives you a number for the character (A-Z is 65-..., a-z is 97-...), and the function chr(int) gives you a character for the number (the reverse from the other one).

Rusca8
  • 533
  • 4
  • 11