Python中的Vigenere密码不适用于大写/小写字母转换

问题描述 投票:0回答:1

作为我目前正在参加的CS50哈佛编程课程的一部分,我正在做一个名为“ Vigenere”的练习。

Vigenere的密码本应该有一个键作为输入,例如“ abcd”。这将根据键中的每个字符对任何明文进行编码,其中a = 0和b = 1等。因此,具有明文“ aa!aa”的键“ abcd”将给出“ ab!cd”。如果明文比密钥长,则应该使密钥循环回到[0]并重新开始,直到所有明文都已编码。非字母应正常打印。

我的程序一切正常(逐行执行,并且符合预期的行为),除了当我收到以大写字母开头,后跟小写字母开头的输入时,我的程序使用小写字母打印了另一个字母,然后它应该给我吗。 EX:键:“巴兹”。明文:“ aaa”。结果:“ bgz”应返回“ baz”。

已经进行了谷歌搜索,调试,但无法弄清楚。也尝试过以许多其他不同方式来执行此操作,但我只是无法使其正常工作。 (很抱歉复制粘贴,您可能会注意到,我已经发布了一个类似的问题,但是那是在C中(这是python),这是另一种错误)

产品编号:

import sys

if len(sys.argv) != 2 or not sys.argv[1].isalpha():
    print("usage: python vigenere.py keyword")
    sys.exit()

cipher = sys.argv[1]
plaintext = input("plaintext: ")

j = 0

def code(j):
    for key in cipher:
        if key.islower():
            return ord(cipher[j]) - 97
        if key.isupper():
            return ord(cipher[j]) - 65

print("ciphertext: ", end="")

for letters in plaintext:
    if letters.islower():
        print(chr(((ord(letters) - 97 + code(j)) % 26) + 97), end="")
        j += 1
    if letters.isupper():
        print(chr(((ord(letters) - 65 + code(j)) % 26) + 65), end="")
        j += 1
    if j == len(cipher):
        j = 0
    if not letters.isalpha():
        print(letters, end="")

print("")
python cs50 vigenere
1个回答
0
投票

代码中的问题是由code函数引起的。

在其中,使用行for key in cipher:,然后用if key.islower():if key.isupper():对其进行检查。

问题是,每次进入code函数时,由于for循环,我们only检查密码中的第一个字母是大写还是小写。

例如。对于密码“ Baz”,j = 0,我们检查B是否为高/低,然后取高。我们立即返回大写字母B

对于密码'Baz',j = 1,我们检查B是否为高/低,然后取高。我们立即返回上A。(当我们应该检查a的上/下,然后返回下a时!)


[通过检查大写或小写密码的正确字母可以解决此问题,可以通过将for key in cipher:替换为key = cipher[j]来解决此问题,就像在下面的块中一样:

def code(j):
    key = cipher[j]
    if key.islower():
        return ord(key) - 97
    if key.isupper():
        return ord(key) - 65

进行更改后,请输入以下内容:

cipher =“ BazBgh”plaintext =“ aaaaAa”

我们得到

密文:bazbGh

© www.soinside.com 2019 - 2024. All rights reserved.