为什么这个scanf语句导致分段错误?

时间:2015-04-07 22:14:03

标签: c segmentation-fault scanf

我一直在对着这堵墙撞了一个小时而且我正在失去理智......我有一段代码(是的,这是作业)抛出一个分段错误,除非我注释掉其中一个我的scanf语句。我曾尝试使用gdb调试问题,但到目前为止我还没有真正了解过这个问题。

以下是代码:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>


char * creditCard(char * ccNumber){
  char * lastFour;

  lastFour = (ccNumber + strlen(ccNumber) - 4);

  return lastFour;
}

void zipCode(int zip){
  printf("The zip code entered is: %d\n", zip);

}

int fuelGrade(int grade){

}

int main(void){
  char * ccNumber = NULL;
  int zip = 0;
  int gasGrade = 0;

  printf("Please Enter Credit Card Number: ");
  scanf("%s", ccNumber);

  printf("Please Enter Your Billing Zip Code: ");
  scanf("%d", &zip);

  printf("Select your Fuel Grade.\n Unleaded(1) Plus(2) Premium(3): ");
  scanf("%d", &gasGrade);


  ccNumber = creditCard(ccNumber);
  printf("****-****-****-%s\n", ccNumber);

  zipCode(zip);

  return 0;
}

当我编译并运行时,我得到以下内容:

Please Enter Credit Card Number: 123413515
Please Enter Your Billing Zip Code: Select your Fuel Grade.
Unleaded(1) Plus(2) Premium(3): 1
Segmentation fault

跳过输入邮政编码,输入燃油等级的任何东西后我立即得到段错误。但是,如果我注释掉 scanf(“%d”,&amp; gasGrade); 行,代码运行正常。

最初我没有初始化变量,我的代码组织方式略有不同,但我似乎无法找到解决此问题的正确方法。 我在这里做错了什么?

感谢您的帮助!

3 个答案:

答案 0 :(得分:4)

因为scanf("%s", ccNumber);ccNumber = NULL一起使用,您将取消引用NULL指针。

"%s"的{​​{1}}说明符需要一个指向有效内存的指针,它可以写入扫描数据,你传递的是scanf()指针,它不会检查指针是否为{ {1}},因此它取消引用NULL指针。

您需要有效的内存,因此您可以在这种情况下使用堆栈,例如

NULL

请注意上面的NULL,它可以防止溢出char buffer[100]; char *ccNumber; if (scanf("%99s", buffer) != 1) problemScanning_buffer_DoNotUse_buffer_In_TheFollowingCode(); ccNumber = creaditCard(buffer); ,并且必须始终检查99的返回值以防止未定义的行为。

答案 1 :(得分:1)

您必须使用malloc为ccNumber分配内存,或者将其定义为数组char ccNumber[17](16位+ \ 0字符)。现在它是指向您初始化为NULL的单个字符的指针。

答案 2 :(得分:0)

您没有为cc编号分配内存(ccNumber为NULL)

读取数字时,您必须清除换行符,但要使用scanf读取另一个值,请自动读取&#39; \ n&#39;它位于输入缓冲区(stdin)中。

printf("Please Enter Your Billing Zip Code: ");
scanf("%d", &zip);

变化:

scanf("%d", &zip);

要:

scanf("%d%*c", &zip);