简体   繁体   中英

Arduino Uno is making errors when doing calculations

So I have been working with my Arduino to make a calculator, and thats what I did. Although, it did not work as I expected it to. When I input simple calculations, it spits it out fine, but when I put in complicated calculations, it goes berserk! It tells me that 9999 * 9 is about -14554 or something like that. Here is the code:

#include <LiquidCrystal_I2C.h>
#include <LCD.h>
#include <Keypad.h>
LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);
const byte ROWS = 4;
const byte COLS = 4;
char keys [ROWS] [COLS] = {
  {'1', '2', '3', '+'},
  {'4', '5', '6', '-'},
  {'7', '8', '9', '*'},
  {'C', '0', '=', '/'}
};
byte rowPins[ROWS] = {13,12,11,10};
byte colPins[COLS] = {9,8,7,6};
Keypad myKeypad = Keypad(makeKeymap(keys), rowPins, colPins, ROWS, COLS);
boolean ansPresent = false;
boolean opSelected = false;
boolean final = false;
String num1, num2;
int answer;
char op;
void setup() {
  lcd.begin(16,2);
  lcd.setCursor(0,0);
  lcd.print("Arduino");
  lcd.setCursor(0,1);
  lcd.print("Calculator");
  delay(2000);
  lcd.clear();
  lcd.setCursor(0,0);
}
void loop(){
  char key = myKeypad.getKey();
  if (ansPresent == false && key != NO_KEY && (key=='1'||key=='2'||key=='3'||key=='4'||key=='5'||key=='6'||key=='7'||key=='8'||key=='9'||key=='0')) {
    if (opSelected == false) {
      num1 = num1 + key;
      lcd.setCursor(0, 0);;
      lcd.print(num1);
    }
    else {
      num2 = num2 + key;
      lcd.setCursor(0, 1);
      lcd.print(num2);
      final = true;
    }
  }
  else if (ansPresent == false && opSelected == false && key != NO_KEY && (key == '/' || key == '*' || key == '-' || key == '+')) {
    opSelected = true;
    op = key;
    lcd.setCursor(15, 0);
    lcd.print(op);
    lcd.setCursor(15, 1);
    lcd.print("=");
  }
  else if (ansPresent == false && final == true && key != NO_KEY && key == '=') {
    if (op == '+'){
      answer = num1.toInt() + num2.toInt();
    }
    else if (op == '-') {
      answer = num1.toInt() - num2.toInt();
    }
    else if (op == '*') {
      answer = num1.toInt() * num2.toInt();
    }
    else if (op == '/') {
      answer = num1.toInt() / num2.toInt();
    }     
      lcd.clear();
      lcd.setCursor(0,0);
      lcd.print(answer);
      ansPresent = true;
  }
  else if (key != NO_KEY && key == 'C') {
    lcd.clear();
    ansPresent = false;
    opSelected = false;
    final = false;
    num1 = "";
    num2 = "";
    answer = 0;
    op = ' ';
  }
}

Is there a reason why it's doing this?

This does look like an overflow on a 16-bit signed integer which is what the Arduino Uno uses internally . Numbers > 32767 cannot be represented with this. It's not an error, it's a limitation of that hardware, it's just 16-bit.

You need to use multiple int values in order to hold anything larger.

The Arduino Uno uses an ATmega. On that board an int is a 16bit signed value with range -32,768 to 32,767.

This means your multiplication overflows and what you see printed out is - according to the documentation - "unpredictable". So make sure you dont do that.

https://www.arduino.cc/reference/en/language/variables/data-types/int/

Notes and Warnings When signed variables are made to exceed their maximum or minimum capacity they overflow. The result of an overflow is unpredictable so this should be avoided. A typical symptom of an overflow is the variable "rolling over" from its maximum capacity to its minimum or vice versa, but this is not always the case. If you want this behavior, use unsigned int.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM