【问题标题】:Using Integer Variable as Index in scanf在 scanf 中使用整数变量作为索引
【发布时间】:2016-01-04 15:15:24
【问题描述】:

我正在尝试在我的函数中执行以下操作,但不断收到分段错误错误。当我尝试使用 [iModify - 1] 作为我的索引时它失败了。

C 中不能使用 int 变量计算作为索引吗?

int modify(pb *PhoneBook)
{
   int x;
   int iModify = 0;
   char name_num[] = {'\0'};
   print(PhoneBook);
   printf("\nWhich entry would you like to modify? ");
   scanf("%d", &iModify);
   printf("\niModify - 1: %d\n", iModify - 1);

   printf("\nModify name or number? ");
   scanf("%s", name_num);
   convert_u(name_num);
   if (strcmp(name_num, "NAME") == 0) {
      printf("\nEnter new name: ");
      scanf("%s %s", PhoneBook[iModify - 1].cFirstName, PhoneBook[iModify - 1].cLastName); //fails here
   }
   else if (strcmp(name_num, "NUMBER") == 0) {
      printf("\nEnter new number: ");
      scanf("%s", PhoneBook[iModify - 1].cNumber); //also fails here
   }
}

【问题讨论】:

  • 1.检查scanf 的返回值 2. scanf("%s", name_num); - 数组name_num 只有一个字符!
  • 3.不要将 scanf 与普通 %s 一起使用:指定最大宽度
  • @Veltas:您可以指定最大值。字符串的字段宽度。
  • @Olaf 的意思是用“plain”来暗示这一点

标签: c arrays scanf


【解决方案1】:

这里的问题是

 char name_num[] = {'\0'};

这里,name_num 的长度为 1 char,这不足以在以后保存 字符串。所以,当你这样做时

scanf("%s", name_num);

您实际上是在调用undefined behavior 的越界写入。

参考:C11,第 §6.7.9 章

如果一个未知大小的数组被初始化,它的大小由最大的索引决定 具有显式初始值设定项的元素。 [...]

为了与您的代码进行比较,name_num 是一个大小未知的数组,它仅由大括号括起来的初始化程序中的单个元素初始化,因此数组的大小将为 1。

解决方案:您必须在定义时明确提及尺寸。你会需要类似的东西

char name_num[32] = {'\0'};     //32 is just for example purpose
....
scanf("%31s", name_num);  // make sure longer inputs don't blow up the buffer

或类似的。


话虽如此,请注意您的int modify() 函数没有 return 任何值。如果调用者使用了返回值,则会再次调用undefined behavior

【讨论】:

  • @SouravGhosh - 谢谢!我忽略了 name_num 字符长度。这行得通。
【解决方案2】:

您在代码中使用了char name_num[] = {'\0'};name_num 的长度为 1 char,太短了,以后无法容纳字符串。

因此,当您阅读 name_num 时,您正在写越界。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2013-12-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-06-09
    • 2020-08-20
    • 2022-06-13
    相关资源
    最近更新 更多