If statement true when false?

Hello, please bare with me as I don't know much about c programming. I have run across a situation that is automatically going to the second if statement even though the variable VibSenseInput is low for the second if statement? Any ideas? In simulation it triggers the first if statement as soon as the VibSenseInput goes HIGH for an instant and goes back low. Though the state is LOW for the second if statement it runs instantly after the first is completed. Code posted below:

Thanks

  if (VibSenseInput == HIGH && SpeakerSwitch == HIGH) {
    SensorCounter++;
    digitalWrite(greenLED, LOW);
    for (counter2 = 0; counter2 < 10; ++counter2) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
  	}

  }   
  	
  	if (VibSenseInput == HIGH && SensorCounter == 1) {
    SensorCounter++;
    digitalWrite(greenLED, LOW);
    for (counter3 = 0; counter3 < 10; ++counter3) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
    }
}

@Coding_Badly might help there.

Use the Serial.print( ) function to prove the value of your variables are what you think they are.


In the Arduino IDE, use Ctrl T or CMD T to format your code then copy the complete sketch.

Use the </> icon from the ‘posting menu’ to attach the copied sketch.

I don't see how VibSenseInput will change from HIGH to LOW after being tested in the first if. Perhaps if you post the complete code...

1 Like

The 2nd if is what you are having issue with?

If VibSenseInput is LOW, none of the posted statements will be executed.

But there is probably quite a bit of code that you forgot to show us. That is where you should be looking for the real problem.

void what_Do_I_Know_How_Much_Code() {
  and_what_the_unposted_code;
  is_assigning_to_variable__VibSenseInput;

You should add serial output to your code to check the reality

void what_Do_I_Know_How_Much_Code() {
  and_what_the_unposted_code;
  is_assigning_to_variable__VibSenseInput;

  Serial.print("VibSenseInput=");
  Serial.print(VibSenseInput);
  Serial.print("  SpeakerSwitch=");
  Serial.println(SpeakerSwitch);
  
  if (VibSenseInput == HIGH && SpeakerSwitch == HIGH) {
    SensorCounter++;
    digitalWrite(greenLED, LOW);
    for (counter2 = 0; counter2 < 10; ++counter2) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
    }
  }

  Serial.print("VibSenseInput=");
  Serial.print(VibSenseInput);
  Serial.print("  SensorCounter=");
  Serial.println(SensorCounter);
  
  if (VibSenseInput == HIGH && SensorCounter == 1) {
    SensorCounter++;
    digitalWrite(greenLED, LOW);
    for (counter3 = 0; counter3 < 10; ++counter3) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(100); // Wait for 100 millisecond(s)
    }
  }
}

Ok, here is the complete code I have been working on. Changing those "if" statements to "else if" stopped every if statement from running like below.

if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 0) {

If I trigger the vibration sensor it runs through each statement fine and makes it to the final "if" if I don't exceed the timeDiff "else if" statement. The final "if" statement executes properly and return back to the if statement where SensorCounter == 0 and will continue. The issue I have now is the "else if" that checks time. like here:

     else if (totalTimediff2 > 12000) {
     SensorCounter = 0;    
    }

My intensions was for the if statement to continue if each is true down to the last if statement as long as each one before it was true, otherwise return SensorCounter to 0 and start over. But if any "else if" statements like above are triggered, it does go back to the top but will no longer advance. Sensor counter stays at 0 at that point. Perhaps my lack of knowledge is to play here. I might not be using the right statement or maybe I have {} wrong? Any ideas how to fix this problem? Thanks

#define greenLED 0
#define speaker 1
#define vibSensor 2
#define redLED 3
#define speakerSwitch 4


int VibSenseInput = 0;
int SensorCounter = 0;
int SpeakerSwitch = 0;
int counter;
int counter2;
int counter3;
int counter4;
int counter5;
int counter6;
int counter7;
int counter8;

unsigned long prevTime = millis();
unsigned long counterTimestamp = millis();
unsigned long counterTimestamp0 = millis();
unsigned long counterTimestamp1 = millis();
unsigned long counterTimestamp2 = millis();
unsigned long counterTimestamp3 = millis();
unsigned long counterTimestamp4 = millis();
unsigned long counterTimestamp5 = millis();
unsigned long counterTimestamp6 = millis();

unsigned long timeDiff1;
unsigned long totalTimediff1;
unsigned long timeDiff2;
unsigned long totalTimediff2;
unsigned long timeDiff3;
unsigned long totalTimediff3;
unsigned long timeDiff4;
unsigned long totalTimediff4;
unsigned long timeDiff5;
unsigned long totalTimediff5;

void setup()
{
  pinMode(vibSensor, INPUT);
  pinMode(speakerSwitch, INPUT);
  pinMode(greenLED, OUTPUT);
  pinMode(redLED, OUTPUT);
  pinMode(speaker, OUTPUT);
}

void loop()
{
  
  unsigned long currentTime = millis();
  VibSenseInput = digitalRead(2);
  SpeakerSwitch = digitalRead(4);
  
  ///This statement is fine
  if (VibSenseInput == LOW && SpeakerSwitch == LOW) {
    digitalWrite(greenLED, HIGH);
    digitalWrite(redLED, LOW);
    digitalWrite(speaker, LOW);
  }
  ///This statement is fine
  if (VibSenseInput == HIGH && SpeakerSwitch == LOW) {
    digitalWrite(greenLED, LOW);
    digitalWrite(speaker, LOW);
    for (counter = 0; counter < 40; ++counter) {
      digitalWrite(redLED, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      delay(50); 
    }
  }
  ///This statement is fine
  if (VibSenseInput == LOW && SpeakerSwitch == HIGH) {
    digitalWrite(greenLED, HIGH);
    digitalWrite(redLED, LOW);
    digitalWrite(speaker, LOW);
  }
 
  ///Works fine if else if timeDiff statement is not triggered.  If those statements bring it back
///to this point, SensorCounter will never increase.
  if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 0) {
    SensorCounter++;
    counterTimestamp1 = currentTime;
    digitalWrite(greenLED, LOW);
    for (counter2 = 0; counter2 < 20; ++counter2) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
  	} 
  }   
  	
  	else if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 1) {
    SensorCounter++;
    counterTimestamp2 = currentTime;
    timeDiff1 = counterTimestamp2 - counterTimestamp1;
    totalTimediff1 = timeDiff1;
    digitalWrite(greenLED, LOW);
    for (counter3 = 0; counter3 < 20; ++counter3) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
    }      
  }
///These are the statements that appear to be causing the issue, every one just like this below
     else if (timeDiff1 > 6000) {
     SensorCounter = 0;    
     }
     
    else if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 2) {
    SensorCounter++;
    counterTimestamp3 = currentTime;
    timeDiff2 = counterTimestamp3 - counterTimestamp2;
    totalTimediff2 = timeDiff1 + timeDiff2;
    digitalWrite(greenLED, LOW);
    for (counter4 = 0; counter4 < 20; ++counter4) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
    } 
  }
     else if (totalTimediff2 > 12000) {
     SensorCounter = 0;    
    }
  
    else if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 3) {
    SensorCounter++;
    counterTimestamp4 = currentTime;
    timeDiff3 = counterTimestamp4 - counterTimestamp3;
    totalTimediff3 = timeDiff1 + timeDiff2 + timeDiff3;
    digitalWrite(greenLED, LOW);
    for (counter5 = 0; counter5 < 20; ++counter5) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
    }      
  }
    else if (totalTimediff3 > 18000) {
    SensorCounter = 0;
    }
  
    else if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 4) {
    SensorCounter++;
    counterTimestamp5 = currentTime;
    timeDiff4 = counterTimestamp5 - counterTimestamp4;
    totalTimediff4 = timeDiff1 + timeDiff2 + timeDiff3 + timeDiff4;
    digitalWrite(greenLED, LOW);
    for (counter6 = 0; counter6 < 20; ++counter6) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
    }  
  }
  	else if (totalTimediff4 > 24000) {
    SensorCounter = 0;
    }
  
    else if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 5) {
    SensorCounter++;
    counterTimestamp6 = currentTime;
    timeDiff5 = counterTimestamp6 - counterTimestamp5;
    totalTimediff5 = timeDiff1 + timeDiff2 + timeDiff3 + timeDiff4 + timeDiff5;
    digitalWrite(greenLED, LOW);
    for (counter7 = 0; counter7 < 20; ++counter7) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
    }  
  }
    else if (totalTimediff5 > 30000) {
    SensorCounter = 0;
    }
  ///This statement works correctly and return to the top and advances normally 
      if (SensorCounter >= 6 && totalTimediff5 < 30000) {
      digitalWrite(speaker, LOW);
    for (counter8 = 0; counter8 < 20; ++counter8) {
      digitalWrite(greenLED, LOW);
      digitalWrite(redLED, HIGH);
      delay(200); 
      digitalWrite(greenLED, HIGH);
      digitalWrite(redLED, LOW);
      delay(200); 
    }
      SensorCounter = 0;  
  }
}

Hi @jessie00721,

I did not really understand your explanation. The reason is that you mix normal words and programmining terms. There is a good chance that you have some misconceptions about how the statements work.

example

Which "if" is the word "if" which "if" is a "if-statement" or "if-else"-statement???
What do you mean with "those" ???
Some lines of code - but which lines of code exactly ????
.
.
So my recommendation is to use only normal words to describe the wanted functionality by actively avoiding programming terms.

You have LEDs and a speaker and are switching them on off under certain conditions

Your code uses a "Vibrationsensor" a "Speakerswitch" a "Countervariable" and somehow a time-difference.

The next step is to describe not the details but giving an overview.
Having the overview will it make much easier to understand what you want to do.

And then writing the details in normal words.
Avoiding all generalised words like "it"s "this", "that", "those" and instead using the word that clearly describes the "thing"

Example
everytime
if

  • the vibesensor sends a LOW-signal
    and
  • the speakerswitch is LOW

==> switch on green LED

etc.

You may find this annoying but writing in a style

If the egg has a weight of 12 grams, pusher-3 shall push the 12gram-egg to conveyor-belt-B so the 12gram-egg is sorted out.

But this writing-style elimates all and every room for different interpretations because it uses the clear-names all and everywhere

If you have a misconception about the programming and your explanation is based on code

it may take dozens of postings until your misconception becomes obvious.
And this is the reason why you should describe it in normal words with repeating the clearnames.

best regards Stefan

What kind of Arduino are you using?

1 Like

Hi, @jessie00721

That is a lot of code.
Did you develop it in stages, and get each stage working before going onto the next.
Then when all stages are working , add them together ONE at a time, each time getting the new code to work.

What do you want your code to do?
What model Arduino?
What is the input and output hardware?

As suggested by @LarryD some Serial.print will probably help.

Thanks... Tom... :smiley: :+1: :coffee: :australia:

This describes nested if(){}'s. Your code does not show nested if(){}'s.

Nested if's, as per the description.



  if (VibSenseInput == LOW && SpeakerSwitch == LOW)
  {
    digitalWrite(greenLED, HIGH);
    digitalWrite(redLED, LOW);
    digitalWrite(speaker, LOW);
    if (VibSenseInput == HIGH && SpeakerSwitch == LOW) 
    {
      digitalWrite(greenLED, LOW);
      digitalWrite(speaker, LOW);
      for (counter = 0; counter < 40; ++counter) 
      {
        digitalWrite(redLED, HIGH);
        delay(50);
        digitalWrite(redLED, LOW);
        delay(50);
      }
      if (VibSenseInput == LOW && SpeakerSwitch == HIGH)
      {
        digitalWrite(greenLED, HIGH);
        digitalWrite(redLED, LOW);
        digitalWrite(speaker, LOW);
      }//if (VibSenseInput == LOW && SpeakerSwitch == HIGH)
    }//if (VibSenseInput == HIGH && SpeakerSwitch == LOW)
  } //if (VibSenseInput == LOW && SpeakerSwitch == LOW)

Is that what you want?

Each If must be true before preceding to the next if. I am sure that is not what you want. The code illustrates your description but will not work.

I'm not sure if the OP wants to have nested ifs
the description is too short
and this is the reason why I say the OP shall describe the wanted functionality
there might be a logic error in the thinking of the OP or a misconcpetion how if-conditions and else-if-s work

we don't know yet

For sure.

Thanks for the all the replies. Think I found the error now. An error is my part for not understanding the program flow and nested statements.

  • Adding "else if" corrected the issue.
    Below is the part that was wrong before.
 if (VibSenseInput == LOW && SpeakerSwitch == HIGH) {
    digitalWrite(greenLED, HIGH);
    digitalWrite(redLED, LOW);
    digitalWrite(speaker, LOW);
  }
 
  if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 0) {
    SensorCounter++;
    counterTimestamp1 = currentTime;
    digitalWrite(greenLED, LOW);
    for (counter2 = 0; counter2 < 20; ++counter2) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
  	} 
  }   

Changed to this:

if (VibSenseInput == LOW && SpeakerSwitch == HIGH) {
    digitalWrite(greenLED, HIGH);
    digitalWrite(redLED, LOW);
    digitalWrite(speaker, LOW);
  }
 
  	else if (VibSenseInput == HIGH && SpeakerSwitch == HIGH && SensorCounter == 0) {
    SensorCounter++;
    counterTimestamp1 = currentTime;
    digitalWrite(greenLED, LOW);
    for (counter2 = 0; counter2 < 20; ++counter2) {
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, HIGH);
      delay(50); 
      digitalWrite(redLED, HIGH);
      digitalWrite(speaker, LOW);
      delay(50); 
      digitalWrite(redLED, LOW);
      digitalWrite(speaker, LOW);
      delay(50); 
  	} 
  }   

Works as intended now. 1 missed "else" caused all the issues.

I’ve been reading this thread. I have some experience with other languages. This ++stuf is important enough to name it after, but I’m still figuring out things.

Does this ++stuff do something in the background? Something I missed? Is x++ the same as ++x?

Which leads to the question:

For ( i = 1; i < 10; ++i)

{

//statements

}

Will this execute the statements when i equals 1? An when i equals 10? 11?

no it is different

initialise variable i with value 1
keep incrementing the variable i as long as the condition i < 10 is true

writing ++i means: increment value of variable i and then after incrementing use the variable

writing i++ means: use value of variable i before incrementing and then increment the value after using the variable

The difference between these two variantes becomes not really obvious in a for-loop
you can see the difference if you use a while-loop instead with a print where directly inside the print the variable gets printed and incremented
something like this

Serial.print("before ++i i=");
Serial.println(i);

Serial.print("i=");
Serial.println(++i); // increment then print

Serial.print("after ++i i=");
Serial.println(i);

.
compared to
.

Serial.print("before i++ i=");
Serial.println(i);
Serial.println(i++); // increment then print

Serial.print("i=");
Serial.println(i++); // increment then print

Serial.print("after i++ i=");
Serial.println(i);

best regards Stefan

Hello stitech

Take a view here to gain the knowledge:

https://www.learncpp.com/cpp-tutorial/increment-decrement-operators-and-side-effects/

Have a nice day and enjoy coding in C++.

the code that demonstrates the difference


byte preIncrVar;
byte postIncrVar;

void setup() {
  Serial.begin(115200);
  Serial.println("Setup-Start");

  preIncrVar  = 2;
  postIncrVar = 2;
  Serial.print("preIncrVar initialised with  2 preIncrVar=");
  Serial.println(preIncrVar);

  Serial.print("postIncrVar initialised with 2 postIncrVar=");
  Serial.println(postIncrVar);
  Serial.println();
  Serial.println();

  while (preIncrVar < 9) {
    Serial.print("print ++preIncrVar preIncrVar=");
    Serial.print(++preIncrVar);

    Serial.print("  |  print postIncrVar++ postIncrVar=");
    Serial.println(postIncrVar++);
  }
}

void loop() {
}

result in the serial monitor

Setup-Start
preIncrVar initialised with  2 preIncrVar=2
postIncrVar initialised with 2 postIncrVar=2


print ++preIncrVar preIncrVar=3  |  print postIncrVar++ postIncrVar=2
print ++preIncrVar preIncrVar=4  |  print postIncrVar++ postIncrVar=3
print ++preIncrVar preIncrVar=5  |  print postIncrVar++ postIncrVar=4
print ++preIncrVar preIncrVar=6  |  print postIncrVar++ postIncrVar=5
print ++preIncrVar preIncrVar=7  |  print postIncrVar++ postIncrVar=6
print ++preIncrVar preIncrVar=8  |  print postIncrVar++ postIncrVar=7
print ++preIncrVar preIncrVar=9  |  print postIncrVar++ postIncrVar=8

best regards Stefan

I was aware of pre increment and post increment from Assembler. I just wondered how C++ was dealing with it.

I recently bought a Nano Every to get me a hobby. To show some differences: I did find out that the declaration ‘byte’ doesn’t work on that board.

In the near future I’ll write a program to answer my own question.

Tutorials I’ve seen so far assume you already know this kind of ‘basic stuff’. I just noticed in @jessie00721 ’s program a difference from the examples I’ve seen before.

Thank you for this new tutorial. I’ll read it.

Hi,

It will count 1, 2, 3, 4, 5, 6, 7, 8, 9
then drop out of the for loop.

Tom... :smiley: :+1: :coffee: :australia:
PS, Write some simple code and try it with Serial.print and IDE monitor