【问题标题】:Arduino multiplication error, +ve * +ve becomes -veArduino乘法错误,+ve * +ve变成-ve
【发布时间】:2014-07-14 05:07:00
【问题描述】:

我正在使用模拟Collatz conjecture 的简单脚本对不同的平台和语言进行基准测试。在测试过程中,我发现我的 arduino 卡在种子 447 上,将 int 13121 乘以三得到 -26173。

我的初始代码是`

//made by Hugo K 
//jun 13 2014




void setup()
{
  Serial.begin(9600);
  while (!Serial)
  {
    ;//wait for serial to connect
  }

}


void loop()
{
  unsigned long starttime;
  starttime = millis();
  for (int i = 1; i <= 500; i++)
  {
    int a = i;
    while (a != 1)
    {
      if (a%2 == 0)
      {
        a = a/2;
      }
      else
      {
        a = (a*3) + 1;
      }
      //Serial.println(a);
    }

  }
  Serial.println(millis() - starttime);
}`

后来被`证实了

void setup()
{
 Serial.begin(9600);
 while(!Serial)
 {
 }

}


void loop()
{
  int i = 13121;
  Serial.println(i *3);

}`

那里的 atmega 微控制器有问题吗?还是 int 13121 有问题会打乱传统的乘法?

【问题讨论】:

    标签: c arduino avr


    【解决方案1】:

    由于此架构中的 sizeof(int) == 2,最大正整数为 0x7FFF (32,767),而在您的情况下为 39363。

    使用 unsigned int 会将最大值增加到 0xFFFF

    使用 unsigned long - 到 0xFFFFFFFF

    【讨论】:

      【解决方案2】:

      您对int 是32 位的期望有问题。使用 AVR,int is only 16 bits;如果需要 32 位,请使用 long

      【讨论】:

      • 他需要 unsigned long 才能得到 32 位,'long' 会给他 31
      • @OlegGryb long 是 32 位 ... 1 个符号位和 31 个精度位
      • 因为他处理的是正数,所以他只能得到 'long' 的最大值是 0x7FFFFFFF,即 31 位,而在 unsigned long 的情况下,最大值将为 0xFFFFFFFF(32 位)。如果不使用无符号类型,他会失去一点。
      • 如果您想要 32 位,请不要使用 long。每当您对数据类型有具体要求时,都会在声明中明确说明。在这种情况下使用uint32_tint32_t
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多