【问题标题】:C variable specified as a long long but recognized as an int指定为 long long 但识别为 int 的 C 变量
【发布时间】:2023-03-31 02:23:01
【问题描述】:

我正在开发一个程序,用于检查我正在参加的 CS50 课程的信用卡号码的有效性(我发誓这是合法的哈哈),我目前正在努力正确获取每个 CC 的前两个号码#检查它来自哪个公司。为了清楚起见,我评论了每个部分的作用,并评论了我的问题出现的地方。

#include <stdio.h>
#include <stdlib.h>
#include <cs50.h>
#include <math.h>
#include <string.h>
int main(void)
{
  long long ccn = get_long_long("Enter CCN: \n");
  int count = 0;
  long long ccn1 = ccn;
  // finds the amount of digits entered and stores that in int count.
  while (ccn1 != 0)
  {
     ccn1 /= 10;
     +count;
  }
  printf("%i \n", count);
  // ln 17- 19 should take int count, subtract two, put that # as the power of 10, 
  // then divide the CC# by that number to get the first two numbers of the CC#.
  long long power = count - 2;
  // here is where i get the error. its a long long so it 
  // should hold up to 19 digits and im only storing 14 max 
  // but it says that 10^14th is too large for type 'int'
  long long divide = pow(10,power);
  long long ft = ccn / divide;
  printf("power: %i \n", power); //ln 20-22 prints the above ints for debug
  printf("Divide: %lli \n", divide);
  printf("First two: %lli \n", ft);
  string CCC;
  // ln 24-35 cross references the amount of digits in the CC#
  // and the first two digits to find the comapany of the credit card
  if ((count == 15) && (ft =  34|37))
  {
    CCC = "American Express";
  }
  else if ((count == 16) && (ft = 51|52|53|54|55))
  {
    CCC = "MasterCard";
  }
  else if ((count = 13|16) && (ft <=49 && ft >= 40))
  {
      CCC = "Visa";
  }
  printf("Company: %s\n", CCC);
}

【问题讨论】:

  • 使用pow 进行整数计算是个坏主意。
  • 不是你的问题,但你可能不想使用这个:else if ((count == 16) &amp;&amp; (ft = 51|52|53|54|55))。首先,| 是按位或不合逻辑的,您应该使用 || 并且您不能以您所做的方式链接它。而= 是赋值运算符,而不是相等。
  • 从一个初学者到另一个,你的猜测和我的一样好在C语言中,这意味着我们的两个猜测都可能是错误的,即使我们观察它们“起作用”,因为即使是早期的细微错误也意味着我们研究的整个基础都建立在错误的假设之上。因此,作为初学者,我们需要一种不同的方法来确保我们教科书的有效性。

标签: c variables cs50 long-long


【解决方案1】:

第一个问题是循环中的+count。这应该是++count。因此,count 保持在 0 和 power = -2。你可以避免所有那些权力的东西。您已经有了循环,您可以使用它来获取前两位数:

int ft = 0;
while (ccn1 != 0)
{
    // When you are down to 10 <= ccn1 < 100, store it
    if (ccn1 < 100 && ccn1 > 9) ft = ccn1;
    ccn1 /= 10;
    ++count;
}

您的第二个问题是如何进行比较。

if ((count == 15) && (ft =  34|37))

首先,= 是赋值,== 测试相等性。其次,| 是按位或,|| 是逻辑或。第三,您不能像这样测试多个值。正确方法:

if ((count == 15) && (ft == 34 || ft == 37))

【讨论】:

  • 我已经完成了所有这些操作,但我仍然遇到同样的错误:credit.c:18:18: runtime error: value 1e+14 is outside of the rangeable value of type 'int'
  • @NoahSparks long long 应该可以工作(请参阅此测试:ideone.com/YymSkG)。但是,如果您使用我提出的while 循环,您可以删除所有这些(从循环之后到string CCC;),因为所有代码所做的只是获取我的循环已经提供的ft
  • @JohnnyMopp 实际上,我正在考虑写一个不鼓励在这里使用long long 的答案。最重要的是,get_long_long 首先以我们需要的形式(十进制数字序列)从标准输入读取输入,然后转换为long long 并丢弃该数组是一种浪费。数组是我们应该在这里验证的。此外,在什么用例中适合使用 negative(使用 - 前缀)、octal(使用 0 前缀)或 hexadecimal i>(使用0x 前缀)用户输入转换为信用卡号
  • 本书鼓励学生在工作中使用错误的工具。这是不幸的,但并不意外......至少对我来说,因为尽管高级内存泄漏不是错误,但仍使用了整个&lt;cs50.h&gt; 包含;这是一个功能,因为作者认为scanffgetsfgetc 对你来说太难学了,我认为这很冒犯。尽管如此,这当然不是因为意料之中而不能接受的;我们必须接受我们所期望的,对吧?毕竟,一本把你当作婴儿一样微妙地对待你的书不太可能像一本尊重你的书那样教你……
  • 原来我记错了。马兰不希望你使用scanffgetsfgetc的原因是因为他认为mallocfree太难学了。更糟糕的是,这些函数都不需要mallocfree。我怀疑他自己也有点糊涂了,他的意思是写scanffgetsfgetc太难学了;它们非常困难且具有欺骗性,但与 C 语言的其他部分一样,所以我仍然认为马兰(可能是无意的,虽然很微妙)侮辱了他的学生。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-03
  • 2011-11-08
  • 2011-05-08
  • 1970-01-01
  • 1970-01-01
  • 2015-06-10
相关资源
最近更新 更多