Программа Caesar Cipher работала, но сейчас не работает (помогите, пожалуйста) - Python 3
Я пишу код Цезаря Шифра для части контролируемой оценки. Я построил полностью функционирующую программу, и я подумал, что подозревал ее, но после изменения нескольких вещей я пошел, чтобы проверить, и все пошло не так!
Код довольно неопрятный, но я немного устал от кодирования этого сейчас и перешел в Интернет, чтобы узнать мнение других.
Код:
answer ="C"
while answer == "C":
lettersList=['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','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']
def menu():
userChoice=input("Would you like to encrypt or decrypt a message? E or D.\n").lower()
while userChoice != "e" and userChoice != "d":
print("Invalid.")
userChoice=input("Would you like to encrypt or decrypt a message? E or D.\n").lower()
print("\n")
return userChoice
def getPlaintext():
plaintext= input("Please enter the message you would like encrypted/decrypted\n").lower()
while plaintext.isalpha() == False:
print("Invalid")
plaintext=input("Please enter the message you would like encrypted/decrypted\n").lower()
print("\n")
return plaintext
def getKey():
key=int(input("Please enter a key. 1-26\n"))
while key > 26 or key < 1:
print("Invalid.")
key=int(input("Please enter a key. 1-26\n"))
print("\n")
return key
def encryptText(plaintext,key):
characterNumber = 0
newMessage = ""
for characters in plaintext:
character = plaintext[characterNumber]
characterPosition = lettersList.index(character)
newPosition=character+key
newLetter = lettersList[newPosition]
newMessage = (newMessage+newLetter)
characterNumber= characterNumber+1
print(newMessage)
def decryptText(plaintext,key):
characterNumber = 0
newMessage = ""
for characters in plaintext:
character = plaintext[characterNumber]
characterPosition = lettersList.index(character)
print(characterPosition)
newPosition=characterPosition-key
newLetter = lettersList[newPosition]
newMessage = (newMessage+newLetter)
characterNumber= characterNumber+1
newMessage = (newMessage.lower())
print(newMessage)
userChoice=menu()
plaintext=getPlaintext()
key=getKey()
if userChoice == "e":
encryptText(plaintext,key)
elif userChoice == "d":
decryptText(plaintext,key)
print(newMessage)
2 ответа
В вашем коде есть несколько простых орфографических ошибок, которые мешают правильному функционированию. for characters in plaintext:
должно быть for character in plaintext:
- в своем коде вы создаете новую переменную characters
который нигде не используется. Правильная функция шифрования с комментариями выглядит так:
def encryptText(plaintext, key):
newMessage = ""
for character in plaintext: # 'character' holds each letter from 'plaintext'
characterPosition = lettersList.index(character)
newPosition = characterPosition + key # shift the index, not the character!
newLetter = lettersList[newPosition]
newMessage = newMessage + newLetter # append new letter to new message
print(newMessage)
Чтобы это правильно работало на lettersList
только с одним вхождением каждого символа (то есть длиной 26) вам нужно проверить, что смещенный индекс не выходит за пределы; то есть символ не больше 26. Если это так, то вычтите 26, как это
newPosition = characterPosition + key
if newPosition >= len(lettersList) then:
newPosition -= len(lettersList)
или используйте оператор по модулю, как предложено. Это должно дать вам представление о том, как изменить функцию расшифровки так, чтобы она также "оборачивалась".
В decypryptText newPosition может быть отрицательным. В этом случае вы должны обернуть весь алфавит. Лучший способ сделать это - использовать оператор%:
newPosition = (characterPosition - key) % len(lettersList)
Между прочим, использование этого в encryptText также позволяет вам создавать в письмах lettersList только одну копию алфавита вместо двух копий, которые вы используете.
Есть и другие вещи, которые можно отшлифовать в этом коде, но они не так важны, как этот.
Редактировать: если вы хотите использовать заглавные буквы для decryptText, вы можете сделать decryptText просто вернуть newMessage.upper(). Таким же образом вы можете заставить encryptText возвращать newMessage.lower().