c - c 中的分割错误,第 2 周凯撒,cs50x 哈佛课程
问题描述
所以我在哈佛cs50在线课程(2021x版)的第2周。我们应该编写一个加密文本的程序,将每个字母的 ASCII 码移动一定的量,由用户通过命令行决定。这是完整的问题。我快完成了,但是当我尝试运行程序时(它编译得很好),它告诉我有一个分段错误。我真的不明白这个问题。我读过这个问题与访问无法访问的某个内存部分有关?我该如何解决这个问题?先感谢您!这是我的代码..
#include <stdio.h>
#include <cs50.h>
#include <ctype.h>
#include <string.h>
int main(int argc, string argv[])
{
int k, i;
if (argc == 2 && isdigit(argv[1]) && argv[1] > 0)
{
k = (int) argv[1];
string plaintext = get_string("plaintext: ");
printf("cyphertext: ");
for (i = 0; i < strlen(plaintext); i++)
{
if (islower(plaintext[i]) || isupper(plaintext[i]))
{
printf("%c", (((plaintext[i] + k) - 97) % 26) + 97);
return 0;
}
}
}
else
{
printf("Usage: ./caesar key");
return 1;
}
}
解决方案
我在哈佛 cs50 在线课程的第 2 周
我很遗憾听到这个消息。您的大多数问题都源于糟糕的 CS-50 类,它诱使您相信 C 以某种方式具有预制的糖衣字符串类。它没有,它只有以空终止结尾的原始字符数组,因此大多数字符串操作都是手动的。
其他问题来自在向您指出错误时不听编译器。这里有几个:
isdigit(argv[1])
没有意义。一个好的编译器会告诉你很多,例如clang:警告:从'string'(又名'char *')转换为更小的整数类型'int'
您比较一个指向字符串的指针,而
isdigit
需要一个字符。为了使用isdigit
,您必须在循环中为字符串的每个字符调用它。argv[1] > 0
没有意义,因为它将指针与 0 进行比较。错误:指针和零之间的有序比较
k = (int) argv[1];
也没有意义。警告:从'string'(又名'char *')转换为更小的整数类型'int'
要将字符串转换为整数,必须使用
strtol
函数,例如k = strtol(argv[1], NULL, 10)
. 它带有您可能也想使用的各种错误处理。而且因为
k
包含废话-实际上它包含转换为整数的内存地址,所以plaintext[i] + k
也变得废话。if (islower(plaintext[i]) || isupper(plaintext[i]))
没有意义,它说“如果一个字符是小写还是大写”。嗯,大概是吧?相反,您可能打算使用toupper
或tolower
执行所有计算,无论用户键入什么内容,都以大写或小写形式进行。
推荐阅读
- ruby-on-rails - 调整范围规则作为acts_as_tenant 的一部分?
- swagger - Swashbuckle 版本控制选择默认的 API 版本出现在 Swagger
- python-3.x - 如何在全局中捕获 GRPC python 错误
- encryption - 数字签名文档中的实际数据
- android - Android 进度条未显示在自定义视图中
- r - “rstanarm 不允许使用重复的组特定术语的公式”,我该如何解决这个问题?
- r - ggplot没有按照我预期的方式读取数据框
- parsing - 如何在 Putty 中进一步处理以从解析服务器获取详细信息
- angular - Angular ng2 谷歌图表未使用新数据更新
- r - 使用纯素包中的 adonis 在 R 中进行双向 PERMANOVA,并进行事后测试