【问题标题】:Comparing a user input string to one that is stored in a pointer. C将用户输入字符串与存储在指针中的字符串进行比较。 C
【发布时间】:2018-04-03 14:22:40
【问题描述】:

我正在尝试编写一个程序来比较用户输入的内容与存储在指针中的单词。代码如下

int c_s(char*, char*);

int main()
{
printf("Hate crime reporting system\n\n\n");

printf("If the crime you are reporting is an emergency,\nplease call 999, do 
not proceed any further with this form\n\n\n\nPlease press enter to confirm 
you have read the above and continue\n");
char enter = 0;
while (enter != '\r' && enter != '\n') { enter = getchar(); }


int a;
long long int g;
char *b, *e;
char *c = "witness";
char *d = "yes";
*c = (long long int) &g;


 printf("Are you a victim or witness of the crime?\nPlease answer 
 victim/witness\n");}
 scanf("%s", b);  
    int r = strcmp (b, c);
    if(r == 0){    
    printf("Do you know who the witness is? Please answer yes/no\n");}
    scanf("%s", d);
       int f = strcmp(e, d);
       if (d = "no") goto NEXT;
       if(e == 0){
         printf("Please enter their details including phone number and 
address");}

NEXT:

当用户对“您是受害者还是证人”的问题回答“证人”时,我希望代码继续并询问下一个问题,如果他们回答“是或否”,则再次相同问题“你知道证人是谁吗?”。当我运行这段代码时,我得到一个溢出错误。我是编码新手,所以如果有人能提供如何完成这项工作的示例代码,我将不胜感激。我不确定是否我使用了错误的指针还是我应该使用数组?

还有人可以解释一下我将如何使这个 if 语句,这意味着如果用户输入“受害者”作为上述问题的答案,程序将继续“下一步:”

【问题讨论】:

  • 没有与指针 b 关联的内存。在有内存之前,您不能将数据放入该指针中。
  • *c = (long long int) &g; - 哎呀

标签: c arrays string pointers


【解决方案1】:

在我们解决你的字符串问题之前,先看看这一行:

printf("Are you a victim or witness of the crime?\nPlease answer victim/witness\n");}

它以} 结尾,似乎与main 的开头相匹配。 至此,您已经结束了 main 函数,剩下的代码甚至都不是函数的一部分。这甚至可能无法编译。


要获取字符串输入,您必须确保有可用于字符串的内存:

char *b;     // WRONG: Uninitialized pointer.
char b[500]; // CORRECT: b can hold up to 499 bytes (+ one \0 at the end)
scanf("%s", b); // Get input into the memory you declared.

另外,你必须确保内存是可写的:
这个问题比较微妙,很多 C 程序员都很难解决这个问题

char *d = "yes";     // WRONG: "yes" is a constant string in your program, it cannot be changed.
char d[200] = "yes"; // CORRECT: d is 200 bytes, and is initially set to "yes".  It can be changed later.

即使在部分程序中正确使用了strcmp,您仍然尝试这样做:

if (d = "no") goto NEXT;
  • 您不能在 C 中以这种方式进行字符串比较。
  • 即使可以,它也会使用== 而不是单个=
  • 永远不要使用goto(除非你希望被velociraptor攻击)

在这一行中,您引用了变量 e,但您从未将其设置为值。

int f = strcmp(e, d);

在这一行中,您将 e 视为整数,但它被声明为 char*
(它仍然没有有效值)

if(e == 0) {

【讨论】:

    【解决方案2】:

    字符串永远不能“存储在指针中”,这正是您的问题。您只需输入scanf() 未初始化的指针b。这有一个随机值并且不指向任何可用内存,因此当scanf() 尝试在那里写入时,您的程序会崩溃。

    解决方案:为scanf() 提供写入内存。要么将b 声明为数组(例如char b[256];),要么使用malloc() 动态分配内存。然后确保您写入的字节数不超过您保留的字节数。如果输入较大,scanf("%s", ...) 将始终溢出任何缓冲区,因此请使用带有scanf() 的字段宽度——请参阅manual page

    更好的是,不要使用scanf()。您可能想阅读我的beginners' guide away from scanf 了解更多信息。

    【讨论】:

      【解决方案3】:

      b 是一个未初始化的指针。因此,您的 scanf 的效果是未定义的行为。像

      char b[100];
      

      将堆栈上的 100 字节空间分配给b。然后,您需要采取措施确保scanf 从标准输入读取的字节数不超过 99 个。

      c 首先被初始化为指向字符串"witness",这很好,但是这一行:

      *c = (long long int) &g;
      

      将第一个字节设置为g 地址的最低字节。完全没有必要,去掉它。

      下一个scanf 扫描到d 设置为文字字符串"yes" 我认为这也是未定义的行为,但无论如何它都是错误的。您应该为e(根据b)分配一些空间并扫描到它。

      strcmp 之后的比较应该使用f 而不是eprintf 应该真的有一个\n

      顺便说一下,这个例子展示了使用描述性变量名的价值。在两个地方,您使用了错误的变量,但如果您以描述性方式命名它们,例如f => comparisonResult 你可能已经避免了混淆。

      【讨论】:

        【解决方案4】:

        一些注意事项可以让您继续前进: 1. 声明字符串时,必须指定它的大小。字符串是一个字符数组,c 中数组的声明应该给出一个大小(至少字符数+1),如下所示:

        char c[10] = "witness";
        
        1. 如果字符串匹配,strcmp 返回 0。

        【讨论】:

          【解决方案5】:

          此行错误,因为字符串不能存储在指针中

          char *c = "witness";
          char *d = "yes";
          

          为此,您需要先为该指针分配内存

          char *c=(char*)malloc(strlen("witness")*sizeof(char));
          char *d=(char*)malloc(strlen("yes")*sizeof(char));
          strcpy(c,"witness");
          strcpy(c,"yes");
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2014-11-06
            • 1970-01-01
            • 2023-03-10
            • 1970-01-01
            • 2020-02-24
            • 2022-11-03
            • 1970-01-01
            相关资源
            最近更新 更多