Pages: [1]   Go Down
Author Topic: Problem with if-else ladder  (Read 964 times)
0 Members and 1 Guest are viewing this topic.
0
Offline Offline
Newbie
*
Karma: 0
Posts: 5
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Hello, I am having very strange problem.
My program code is below:
val = analogRead(A6);

  if(val<=312)
    tem=map(val,0,312,700,400);
  else if(312<val<=455)
    tem=map(val,312,455,400,300);
  else if(455<val<=612)
    tem=map(val,455,612,300,200);
  else if(612<val<=745)
    tem=map(val,612,745,200,100);
  else if(745<val<=1023)
    tem=map(val,745,1023,100,0);
 Serial.println(val);
Serial.println.(tem);

I am trying to read analog reading and convert it using map function.
Now here when the analog value val is 991 the program goes to the second if in the if-else ladder.
It means that(312<val<=455) condition becomes true when val=991 !!!!! and that results in value of "tem" according to the map function in second if statement. In my case the value of tem becomes -74. The program should go to last if statement when value of val is 991. but it doesn't. Please help me out here.

My arduino board: Arduino mega(old one)
Software: Arduino 0022
Logged

Seattle, WA USA
Offline Offline
Brattain Member
*****
Karma: 601
Posts: 48543
Seattle, WA USA
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Code:
else if(312<val<=455)
You can not do this. You must explicitly form two comparisons:
Code:
else if(312 < val && val <=455)
Logged

Guildford, UK
Offline Offline
Full Member
***
Karma: 0
Posts: 217
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Actually the first of the two comparisons is redundant in each case as the previous conditional tests have already accounted for those values.

I would modify your code to be:

Code:
  if(val<=312)
    tem=map(val,0,312,700,400);
  else if(val<=455)
    tem=map(val,312,455,400,300);
  else if(val<=612)
    tem=map(val,455,612,300,200);
  else if(val<=745)
    tem=map(val,612,745,200,100);
  else
    tem=map(val,745,1023,100,0);

Note I've also removed the final if since it's redundant.

Iain
Logged

Atlanta, GA
Offline Offline
Jr. Member
**
Karma: 0
Posts: 86
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I also think you want greater than and not less than
I also think that you don't need the greater than's because of your order

Code:
else if(312 > val && val <=455)

Code:
else if(val <=455)
Logged

Seattle, WA USA
Offline Offline
Brattain Member
*****
Karma: 601
Posts: 48543
Seattle, WA USA
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Code:
else if(312 > val && val <=455)
If 312 is greater than val, that means that val is less than 312. That is not consistent with the original, but incorrect, code.
Logged

Atlanta, GA
Offline Offline
Jr. Member
**
Karma: 0
Posts: 86
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

sorry about transposing: val > 312

but if it's checked before (as in the example given) then it's useless to check again

Logged

Global Moderator
Netherlands
Offline Offline
Shannon Member
*****
Karma: 212
Posts: 13531
In theory there is no difference between theory and practice, however in practice there are many...
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset


unless the type of val is volatile ....  (sorry to make it difficult)

if the else part was missing the first condition is mandatory
Code:
if(val<=312) tem=map(val,0,312,700,400);
if(312 > val && val<=455) tem=map(val,312,455,400,300);
if(455 > val && val<=612) tem=map(val,......
etc
but the code of sixeyes is optimized => more efficient as the number of tests is minimized
Logged

Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

0
Offline Offline
Newbie
*
Karma: 0
Posts: 5
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

I just removed all "else" statements ad everything is working cool now. I think if(x<val<=y) type of condition checking is supported in arduino. I also tried other methods and they worked as well.. Thanks guys....
Logged

Guildford, UK
Offline Offline
Full Member
***
Karma: 0
Posts: 217
Arduino rocks
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Quote
I think if(x<val<=y) type of condition checking is supported in arduino

If you really want this check you can write it as:

Code:
if (x < val && val <= y)

The code you wrote was a mathematical expression but in C/C++ (as used on the arduino) you have to use binary expressions (i.e. only two values to an operator. So to implement what you want needs three bits (x < val), (val <= y) and &&. The && is C's logical and operator combining the two comparisons.

BTW the code I posted in reply #3 is much more efficient that your original (see below) as you are performing many more comparisons that is necessary. In the first else if you have already performed the 312 < val in the preceding if (as val <= 312 is the opposite of 312 < val) so this part of the expression will always be true if it is executed (a waste of clock cycles and code memory). It is the same for each else if. This final else if if should be replaced by an else as the analog read will produce a value between 0 - 1023 (so the test in this expression will always be true).

As a side issue: if val was not limited to the range 0 - 1023, for values outside this range tem would be uninitialised. When I initialise a variable in a if/else if ladder, I always have an else or initialise the variable before the first if.

Code:
  if (val <= 312)
    tem = map(val, 0, 312, 700, 400);
  else if(312 < val && val <= 455)
    tem = map(val, 312, 455, 400, 300);
  else if (455 < val && val <= 612)
    tem = map(val, 455, 612, 300, 200);
  else if (612 < val && val <= 745)
    tem = map(val, 612, 745, 200, 100);
  else if(745 < val && val <= 1023)
    tem = map(val, 745, 1023, 100, 0);

Hope that helps.

Iain
Logged

Global Moderator
Netherlands
Offline Offline
Shannon Member
*****
Karma: 212
Posts: 13531
In theory there is no difference between theory and practice, however in practice there are many...
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset


Quote
if(x<val<=y)

As sixeyes said this is a correct mathematical expression but is doesn't do what you want.

try this sketch
Code:
void setup()
{
  Serial.begin(115200);
  int val = 100;
 
  if (10 < val <= 50) Serial.println("BUG");
  else Serial.println("OK");
}
void loop(){}

It prints BUG because the precedence/order of comparison operators is from left to right and the outcome of a compression is either 0(false) or 1(true).
1) 10 < 100 <=50 is evaluated:
2) 10<100 ?? => true so (10<100) is replaced by 1
3) 1 <= 50 ?? => true  ==> print bug

Another variation:
Code:
void setup()
{
  Serial.begin(115200);
  int val = 100;

  if (10 > val > -1 ) Serial.println("BUG");
  else Serial.println("OK");
}

void loop(){}

Logged

Rob Tillaart

Nederlandse sectie - http://arduino.cc/forum/index.php/board,77.0.html -
(Please do not PM for private consultancy)

Pages: [1]   Go Up
Jump to: