CS50 - C -问题集 2 - 替换 - 输出无效的 ASCII 文本

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

这是我在 stackoverflow 上的第一篇文章,所以我希望我做得正确,如果没有的话请告诉我。

我的代码有问题,但我看不到。 CS50 检查给我一个输出错误: ** ":( 使用 yukfrnlbavmwzteogxhcipjsqd 作为密钥将“This is CS50”加密为“Cbah ah KH50”。 原因: 输出无效的 ASCII 文本"**

Thats the code:

#include <cs50.h>
#include <stdio.h>
#include <string.h>
#include <ctype.h>



int main(int argc, string argv[])
{
    if (argc != 2)
    {
        printf("Usage: ./substitution\n");
        return 1;
    }

    string key = argv[1];

    if (strlen(key) != 26)
    {
        printf("The key must contain 26 characters\n");
        return 1;
    }

    for(int i = 0; i < strlen(key); i++)
    {

    if (!isalpha(key[i]))
    {
        printf("Usage: ./substitution\n");
        return 1;
    }

    }

    for (int i = 0; i < strlen(key); i++)
    {
        for(int j = i + 1; j < strlen(key); j++)
        {
            if (toupper(key[i]) == toupper(key[j]))
            {
                printf("Usage: substitution key\n");
                return 1;
            }
        }
    }

    string plaintext = get_string("Plaintext: ");

    printf("ciphertext: ");

    for(int i = 0; i < strlen(plaintext); i++)
    {
        if(isupper(plaintext[i]))
        {
            int letter = plaintext[i] - 'A';
            printf("%c", key[letter]);
        }
        else if(islower(plaintext[i]))
        {
            int letter = plaintext[i] - 'a';
            printf("%c", tolower(key[letter]));
        }
        else if (plaintext[i] == ' ') // Handle spaces
        {
        printf(" ");
        }
        else
        {
            printf("%c",plaintext[i]);
        }
    }
    printf("\n");
    return 0;
}
cs50 substitution
1个回答
0
投票

我根据上面我的原始评论回复您的请求。

首先,尽管我过去分析过其他“CS50”问题,但我的系统上实际上并没有安装哈佛课程;然而,这并没有阻止我过去进行分析和提供建议。将其设置为我的背景后,从我所看到和研究的课程来看,检查程序对代码和答案的分析可能相当挑剔,而您在这里发生的事情似乎是 CS50 检查过程期望要返回的字符串。然而,从技术上讲,您一次打印一个字符。尽管这可能有些迂腐,但您的代码不会打印出以终止符 (' ') 结尾的字符数组。

所以我在评论中建议的是重构你的密码算法。

以下是我关注的代码块。

    string plaintext = get_string("Plaintext: ");

    printf("ciphertext: ");

    for(int i = 0; i < strlen(plaintext); i++)
    {
        if(isupper(plaintext[i]))
        {
            int letter = plaintext[i] - 'A';
            printf("%c", key[letter]);
        }
        else if(islower(plaintext[i]))
        {
            int letter = plaintext[i] - 'a';
            printf("%c", tolower(key[letter]));
        }
        else if (plaintext[i] == ' ') // Handle spaces
        {
        printf(" ");
        }
        else
        {
            printf("%c",plaintext[i]);
        }
    }
    printf("\n");
    return 0;

将加密/密文视为字符串,以下是该代码块的重构版本。

    string plaintext = get_string("Plaintext: ");

    char ciphertext[strlen(plaintext) + 1];         /* Define a character array large enough to hold the inputted string    */

    strcpy(ciphertext, plaintext);                  /* Use standard string function to copy entered string to work string   */

    for(int i = 0; i < strlen(ciphertext); i++)     /* Simplified for loop  */
    {
        if(isupper(ciphertext[i]))
            ciphertext[i] = toupper(key[ciphertext[i] - 'A']);  /* Just replace alphabetical characters with appropriate key value  */
        else if(islower(plaintext[i]))
            ciphertext[i] = tolower(key[ciphertext[i] - 'a']);  /* Just replace alphabetical characters with appropriate key value  */
    }

    printf("Ciphertext: %s\n", ciphertext);

    return 0;

要点如下:

  • 定义了一个工作变量,该变量足够大以包含输入的字符串。
  • 使用标准的“strcpy”函数,将输入的字符串复制到此工作字符串。
  • 使用 for 循环,评估工作字符串中的每个字符是否是大写或小写字符,如果是,则对该字符应用加密过程。
  • 分析和处理完所有字符位置后,将打印出工作字符串。

以下是我使用指定的字符串和密钥进行的测试。

craig@Vera:~/C_Programs/Console/CSsub/bin/Release$ ./substitution yukfrnlbavmwzteogxhcipjsqd
Plaintext: This is CS50
Ciphertext: Cbah ah KH50

正如我所指出的,我的系统上实际上没有 CS50 工具,但您可以尝试一下,因为检查器进程似乎需要一个字符串,而不是连续打印单个字符。

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