C 中的 Vigenere 密码 (CS50)
Vigenere's Cipher in C (CS50)
我已经坚持了一段时间了,我以为我让它工作了好几次只是为了找到更多我忘记的东西。基本上问题集是使用C创建Vigenere Cipher,规则可以找到here
我基本上让它工作了,它只允许正确的字符,如果关键字与消息的长度相同,一切都很好。
我遇到的问题是想办法在消息被加密时重置关键字的循环,所以如果我输入关键字 'A' 和消息 'This is a test' 加密消息应该读作 'This is a test',因为 'A' 值得沿 ASCII table.
移动零
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <stdbool.h>
int main(int argc, char * keyWord[]) {
int cipher[64], i, j, k, l;
char message[128];
// Validation - using alphaCheck Function
if (argc != 2 || alphaCheck(keyWord) == 2) {
return 1;
}
// For loop to convert to upper and set value ie A = 0 B = 1
for (i = 0, j = strlen(keyWord[1]); i < j; i++) {
cipher[i] = (toupper(keyWord[1][i]) - 65);
printf("%i\n", cipher[i]);
}
// Prompt the user for the message to encrypt
printf("Enter your secret message: ");
fgets(message, 128, stdin);
int keyCount = 0;
int p = strlen(keyWord[1]);
if (keyCount < p) {
keyCount++;
} else {
keyCount = 0;
}
for (i = 0, k = strlen(message); i < k; i++) {
if (isspace(message[i])) {
printf(" ");
} else if (isupper(message[i])) {
char c = (message[i] - 65 + cipher[i]) % 26 + 65;
printf("%c", c);
}
else {
char d = (message[i] - 97 + cipher[i]) % 26 + 97;
printf("%c", d);
}
}
}
// Function to check if alphabet characters.
int alphaCheck(char * argv[]) {
int length = strlen(argv[1]), n;
for (n = 0; n < length; n++) {
if (!isalpha(argv[1][n])) {
printf("Characters 'A-Z' for Keyword.\n");
return 2;
}
}
}
以下部分在我留下来展示我如何尝试解决问题但失败时是多余的。
int keyCount = 0;
int p = strlen(keyWord[1]);
if (keyCount < p) {
keyCount++;
} else {
keyCount = 0;
}
首先,您应该启用更多编译器警告。例如,使用 gcc 和我最喜欢的一组标志 (-pedantic -Wall -Wextra -Wundef -Wendif-labels -Wshadow -Wbad-function-cast -Wcast-align -Wwrite-strings -Wstrict-prototypes -Wmissing-prototypes -Wnested-externs -Winline -Wdisabled-optimization -O2
) 我得到:
$ cc prog.c
prog.c: In function ‘main’:
prog.c:12:20: warning: implicit declaration of function ‘alphaCheck’ [-Wimplicit-function-declaration]
if (argc != 2 || alphaCheck(keyWord) == 2) {
^
prog.c:12:3: warning: nested extern declaration of ‘alphaCheck’ [-Wnested-externs]
if (argc != 2 || alphaCheck(keyWord) == 2) {
^
prog.c:8:28: warning: unused variable ‘l’ [-Wunused-variable]
int cipher[64], i, j, k, l;
^
prog.c: At top level:
prog.c:53:5: warning: no previous prototype for ‘alphaCheck’ [-Wmissing-prototypes]
int alphaCheck(char * argv[]) {
^
prog.c: In function ‘alphaCheck’:
prog.c:61:1: warning: control reaches end of non-void function [-Wreturn-type]
}
^
所有这些都应该修复:
- 在
alphaCheck
末尾添加return 0
- 移除
l
- 将
int alphaCheck(char *[]);
放在main
之前(或者将整个函数移到main
之前,使其成为static
)
你的主循环有三种情况。它检查空格、大写字符,其他所有字符均假定为小写字符。您应该检查大写字母、小写字母,并通过不变的方式传递其他所有内容(例如标点符号 .
或 ,
):
if (isupper(message[i])) {
...
} else if (islower(message[i])) {
...
} else {
printf("%c", message[i]);
}
你对 keyCount
的想法不错,但它需要与主循环集成。也就是说,你应该在循环中使用cipher[keyCount]
,而不是cipher[i]
,并且每次这样使用它时都会增加keyCount
。
然后,在每次迭代结束时,您可以检查是否 运行 失调(并重置 keyCount
):
for ( ... ) {
...
if (keyCount >= p) {
keyCount = 0;
}
}
我已经坚持了一段时间了,我以为我让它工作了好几次只是为了找到更多我忘记的东西。基本上问题集是使用C创建Vigenere Cipher,规则可以找到here
我基本上让它工作了,它只允许正确的字符,如果关键字与消息的长度相同,一切都很好。
我遇到的问题是想办法在消息被加密时重置关键字的循环,所以如果我输入关键字 'A' 和消息 'This is a test' 加密消息应该读作 'This is a test',因为 'A' 值得沿 ASCII table.
移动零#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>
#include <stdbool.h>
int main(int argc, char * keyWord[]) {
int cipher[64], i, j, k, l;
char message[128];
// Validation - using alphaCheck Function
if (argc != 2 || alphaCheck(keyWord) == 2) {
return 1;
}
// For loop to convert to upper and set value ie A = 0 B = 1
for (i = 0, j = strlen(keyWord[1]); i < j; i++) {
cipher[i] = (toupper(keyWord[1][i]) - 65);
printf("%i\n", cipher[i]);
}
// Prompt the user for the message to encrypt
printf("Enter your secret message: ");
fgets(message, 128, stdin);
int keyCount = 0;
int p = strlen(keyWord[1]);
if (keyCount < p) {
keyCount++;
} else {
keyCount = 0;
}
for (i = 0, k = strlen(message); i < k; i++) {
if (isspace(message[i])) {
printf(" ");
} else if (isupper(message[i])) {
char c = (message[i] - 65 + cipher[i]) % 26 + 65;
printf("%c", c);
}
else {
char d = (message[i] - 97 + cipher[i]) % 26 + 97;
printf("%c", d);
}
}
}
// Function to check if alphabet characters.
int alphaCheck(char * argv[]) {
int length = strlen(argv[1]), n;
for (n = 0; n < length; n++) {
if (!isalpha(argv[1][n])) {
printf("Characters 'A-Z' for Keyword.\n");
return 2;
}
}
}
以下部分在我留下来展示我如何尝试解决问题但失败时是多余的。
int keyCount = 0;
int p = strlen(keyWord[1]);
if (keyCount < p) {
keyCount++;
} else {
keyCount = 0;
}
首先,您应该启用更多编译器警告。例如,使用 gcc 和我最喜欢的一组标志 (-pedantic -Wall -Wextra -Wundef -Wendif-labels -Wshadow -Wbad-function-cast -Wcast-align -Wwrite-strings -Wstrict-prototypes -Wmissing-prototypes -Wnested-externs -Winline -Wdisabled-optimization -O2
) 我得到:
$ cc prog.c
prog.c: In function ‘main’:
prog.c:12:20: warning: implicit declaration of function ‘alphaCheck’ [-Wimplicit-function-declaration]
if (argc != 2 || alphaCheck(keyWord) == 2) {
^
prog.c:12:3: warning: nested extern declaration of ‘alphaCheck’ [-Wnested-externs]
if (argc != 2 || alphaCheck(keyWord) == 2) {
^
prog.c:8:28: warning: unused variable ‘l’ [-Wunused-variable]
int cipher[64], i, j, k, l;
^
prog.c: At top level:
prog.c:53:5: warning: no previous prototype for ‘alphaCheck’ [-Wmissing-prototypes]
int alphaCheck(char * argv[]) {
^
prog.c: In function ‘alphaCheck’:
prog.c:61:1: warning: control reaches end of non-void function [-Wreturn-type]
}
^
所有这些都应该修复:
- 在
alphaCheck
末尾添加 - 移除
l
- 将
int alphaCheck(char *[]);
放在main
之前(或者将整个函数移到main
之前,使其成为static
)
return 0
你的主循环有三种情况。它检查空格、大写字符,其他所有字符均假定为小写字符。您应该检查大写字母、小写字母,并通过不变的方式传递其他所有内容(例如标点符号 .
或 ,
):
if (isupper(message[i])) {
...
} else if (islower(message[i])) {
...
} else {
printf("%c", message[i]);
}
你对 keyCount
的想法不错,但它需要与主循环集成。也就是说,你应该在循环中使用cipher[keyCount]
,而不是cipher[i]
,并且每次这样使用它时都会增加keyCount
。
然后,在每次迭代结束时,您可以检查是否 运行 失调(并重置 keyCount
):
for ( ... ) {
...
if (keyCount >= p) {
keyCount = 0;
}
}