首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >CS50 Vigenere密码

CS50 Vigenere密码
EN

Code Review用户
提问于 2017-03-19 22:35:53
回答 1查看 127关注 0票数 0
代码语言:javascript
复制
#include <cs50.h>
#include <math.h>
#include <string.h>
#include <ctype.h>
#include <stdlib.h>
#include <stdio.h>

int k = 0;
int convUpperAsciiToAlphaIndex = 65;
int convLowerAsciiToAlphaIndex = 97;
int AlphaIndexWrap = 26;

int main(int argc, string argv[])               // get Key from user via Command-Line Argument
{
                                                // printf("%i\n", i); test print to see value of i 
   if(argc != 2)
        {
            printf("Invalid command line argument (non-alphabetical character)\n");
            return 1;
        }
    string r = argv[1];
    int q = strlen(argv[1]);
    for(int i = 0; i < q; i++)    //iterate every char in string to see if isalpha
    {   
        if(isalpha(r[i]) == 0)
        {
            printf("Invalid command line argument\n");
            return 1;
        }
    }
    printf("plaintext: ");
    string plaintext = get_string();
    if (plaintext != NULL)
    {
        int c = strlen(plaintext);
        printf("ciphertext: ");
                                                    // printf("%i \n", c); test print strlen result
        for(int h = 0; h < c ; h++)
        {
            char d = plaintext[h];
            if(isalpha(d))
            {
                int m = (k % q);                    // Modulo wrap-around index tracking for Key
                int v = (r[m]);
                {
                    if((isupper(d) && isupper(v)))
                    {

                        // Converts Plaintext & Key from Upper ASCii to Alpha Index, ADDS the two resulting INTs (applies the Cipher), applies Modulo Wraparound for Plaintext Index
                        int x = (((d - convUpperAsciiToAlphaIndex) + (v - convUpperAsciiToAlphaIndex)) % AlphaIndexWrap);       

                        // converts back to ASCii
                        int w = (x + convUpperAsciiToAlphaIndex);                                                               
                        printf("%c", toupper(w));
                    }
                    else if((isupper(d) && islower(v)))
                    {
                        int toupper(int v);

                        // Converts Upper Plaintext & Lower Key from ASCii to Alpha Index, ADDS the two resulting INTs (applies the Cipher), applies Modulo Wraparound for Plaintext Index
                        int x = (((d - convUpperAsciiToAlphaIndex) + (v - convLowerAsciiToAlphaIndex)) % AlphaIndexWrap);      

                        // converts back to ASCii
                        int w = (x + convUpperAsciiToAlphaIndex);                   
                        printf("%c", toupper(w));
                    }
                    else if((islower(d) && isupper(v)))
                    {
                        int tolower(int v);

                        // Converts Lower Plaintext & Upper Key from ASCii to Alpha Index, ADDS the two resulting INTs (applies the Cipher), applies Modulo Wraparound for Plaintext Index
                        int x = (((d - convLowerAsciiToAlphaIndex) + (v - convUpperAsciiToAlphaIndex)) % AlphaIndexWrap);  // d - 97 + 2...converts to alpha index from lower and adds Key

                        // converts back to ASCii
                        int w = (x + convUpperAsciiToAlphaIndex);               // converts back to ASCII
                        printf("%c", tolower(w));
                    }
                    else if((islower(d) && islower(v)))
                    {

                        // Converts Plaintext & Key from Lower ASCii to Alpha Index, ADDS the two resulting INTs (applies the Cipher), applies Modulo Wraparound for Plaintext Index
                        int x = (((d - convLowerAsciiToAlphaIndex) + (v - convLowerAsciiToAlphaIndex)) % AlphaIndexWrap);  // d - 97 + 2...converts to alpha index from lower and adds Key

                        // converts back to ASCii
                        int w = (x + convUpperAsciiToAlphaIndex);               
                        printf("%c", tolower(w));
                    }
                    k++;
                }
            }
            else
            {
                printf("%c", (plaintext[h]));       // prints non-alpha chars
            }
        }
        printf("\n");
    }
    return 0;
}
EN

回答 1

Code Review用户

发布于 2017-03-20 16:26:16

在发布的代码中没有使用math.h中可用的任何函数等。包含未被使用的头文件是个坏主意。

在cs50.h中,没有一个函数是可移植的,强烈建议使用实际的C语言类型和C库函数

当命令行参数列表出现问题时,所产生的错误消息应该输出stderr,而不是stdout,并且应该是“使用”消息,类似于:

代码语言:javascript
复制
fprintf( stderr, "USAGE: %s <stringToEncode>\n", argv[0] ); 

函数:get_string()不是cs50.h标头的一部分,也不是在已发布的代码中定义的。也许你的意思是:GetString()。这表明,要么您没有编译发布的代码,要么发布的代码不是您的实际代码。

一般来说,如果代码使用的是'a‘或'A’这样的文字,而不是硬编码的值,那么这是非常容易理解的,而26是一个“魔术”数字。神奇的数字没有根据。建议使用enum语句或#define语句给“魔术”编号一个有意义的名称,然后在整个代码中使用有意义的名称。

在新代码中,这些行:

代码语言:javascript
复制
int convUpperAsciiToAlphaIndex = 65;
int convLowerAsciiToAlphaIndex = 97;
int AlphaIndexWrap = 26;

只是把代码弄得乱七八糟,占用堆栈空间。

建议将所有出现的convUpperAsciiToAlphaIndex替换为'A‘。

建议用'a‘替换所有出现的convLowerAsciiToAlphaIndex

建议更换这一行

代码语言:javascript
复制
int AlphaIndexWrap = 26;

通过以下方式:

代码语言:javascript
复制
#define ALPHABET_SIZE 26

并将所有出现的AlphaIndexWrap替换为ALPHABET_SIZE

变量名应该指示contentusage (或者两者都更好)。

此代码:

代码语言:javascript
复制
   if(argc != 2)
    {
        printf("Invalid command line argument (non-alphabetical character)\n" );
    }

不正确,也不向用户传达问题所在,也不向stderr输出此错误消息。请参阅我先前关于如何更正这些代码行的评论。

为了便于阅读和理解:单独的代码块(用于,如果,否则,时间,do...while,开关,大小写,默认)通过一个空白行。

这一行:

代码语言:javascript
复制
printf("Invalid command line argument\n");

有问题:

  1. 未能将错误消息输出到stderr
  2. 未能向用户提供命令行参数不正确的任何理由。

在代码花费大量精力验证命令行参数之后,它将从stdin (即用户)获得一个全新的字符串来进行实际加密。而新的字符串根本没有被验证。

票数 1
EN
页面原文内容由Code Review提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://codereview.stackexchange.com/questions/158279

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档