if(val == 0) игнорируется, когда он содержит другой вложенный оператор if()
Проблема: В следующем примере, несмотря на то, что complexManoeuvre == 3, Serial.print(CTA5: "); ...
выполняется.
void loop() {
if(complexManoeuvre == 0) {
if(timeisup == true && goingForwards == 1) { // Если время истекло при движении вперед, предположим, что оно застряло
goingForwards = 0;
Serial.print("CTA4: "); stuck(stk);
}
if(timeisup == true && goingForwards != 1) {
Serial.print("CTA5: "); Serial.print(complexManoeuvre); forward(fwd);
}
}
}
Однако, если я включу первое условие в другие два утверждения if(), то это сработает:
if(complexManoeuvre == 0 && (deltaBegan >= manoeuvreFor) && goingForwards == 1) {
goingForwards = 0;
Serial.print("CTA4: "); Serial.print(complexManoeuvre); stuck(stk);
}
if(complexManoeuvre == 0 && (deltaBegan >= manoeuvreFor) && goingForwards != 1) {
//Serial.print("complexManoeuvre == "); Serial.println(complexManoeuvre);
Serial.print("CTA5: "); Serial.print(complexManoeuvre); forward(fwd);
}
Будучи полностью озадаченным, я заподозрил проблему с компилятором, поэтому я переустановил Arduino, чтобы очистить оболочку Meguno-link avrdude, но проблема остается.
Полный код (для робота-пылесоса) выглядит следующим образом, максимально сокращенный для упрощения чтения:
const int fwd = 12000; // длительность мс
const int stk = 1600;
unsigned long beganManoeuvre; // миллис время начала маневра
int manoeuvreFor; // Длительность
unsigned long lastStuck;
byte goingForwards; // Да или нет
byte complexManoeuvre; // 0 = нет, 1 = центр, 2 = застрял, 3 = прогресс
byte progress; // Прогресс сложного управления
void setup() {
Serial.begin(9600);
Serial.print(F("CTA0: ")); spinR(4800); // Вращение на 360 градусов
}
void loop() {
bool timeisup = false;
if((millis() - beganManoeuvre) >= manoeuvreFor) {
timeisup = true;
}
if(complexManoeuvre != 0 && timeisup == true) { // Если часть пути через a в сложном
switch(complexManoeuvre) { // ..маневр (например; застрял)
case 1:
// делать другое()
break;
case 2:
Serial.print(F("CTA2: ")); stuck(manoeuvreFor); // возврат к сложному маневру
break;
}
}
// если(сложный маневр == 0 && timeisup == true && Движение вперед == 1) {
// Движение вперед = 0;
// Serial.print("CTA4: "); Serial.print(сложный процесс); застрял (stk);
// }
// если(complexManoeuvre == 0 && timeisup == true && Вперед!= 1) {
// //Serial.print("complexManoeuvre == "); Serial.println(complexManoeuvre);
// Serial.print("CTA5: "); Serial.print(complexManoeuvre); вперед (fwd);
// }
if(complexManoeuvre == 0) {
if(timeisup == true && goingForwards == 1) { // Если timeisup при движении вперед, предположим, что застрял
goingForwards = 0;
Serial.print("CTA4: "); stuck(stk);
}
if(timeisup == true && goingForwards != 1) { // Если закончен еще один маневр, двигайтесь вперед
if(complexManoeuvre != 0) Serial.println("What the?!");
Serial.print("CTA5: "); Serial.print(complexManoeuvre); forward(fwd);
}
}
}
void stuck(int dur) {
Serial.print(F("void stuck(int dur == ")); Serial.println(dur);
switch(progress) {
case 0:
Serial.print(F("CTA26: "));
complexManoeuvre = 2;
reverse(dur);
progress = 1;
break;
case 1:
Serial.print(F("CTA27: "));
spinR(dur);
progress = 2;
break;
case 2: // Сброс
progress = 0;
complexManoeuvre = 0;
lastStuck = millis();
break;
}
}
void forward(int dur) {
Serial.print(F("void forward(int ")); Serial.print(dur);
if(goingForwards != 1) {
Serial.print(F(") >> if(goingForwards != 1) then do"));
goingForwards = 1;
beganManoeuvre = millis();
manoeuvreFor = dur;
digitalWrite(9, HIGH);
digitalWrite(10, LOW);
digitalWrite(11, HIGH);
digitalWrite(12, LOW);
}
Serial.println();
}
void reverse(int dur) {
Serial.print(F("void reverse(int dur == ")); Serial.println(dur);
beganManoeuvre = millis();
manoeuvreFor = dur;
digitalWrite(9, LOW);
digitalWrite(10, HIGH);
digitalWrite(11, LOW);
digitalWrite(12, HIGH);
}
void spinR(int dur) {
Serial.print(F("void spinR(int dur == ")); Serial.println(dur);
beganManoeuvre = millis();
manoeuvreFor = dur;
digitalWrite(9, LOW);
digitalWrite(10, HIGH);
digitalWrite(11, HIGH);
digitalWrite(12, LOW);
}
Сомнительный последовательный вывод таков:
1) 19:59:31.964 -> CTA0: void spinR(int dur == 4800
2) 19:59:36.765 -> CTA5: 0void forward(int 12000) >> if(goingForwards != 1) then do
3) 19:59:48.771 -> CTA4: void stuck(int dur == 1600
4) 19:59:48.811 -> CTA26: void reverse(int dur == 1600
5) 20:11:12.695 -> What the?!
6) 19:59:48.851 -> CTA5: 2void forward(int 12000) >> if(goingForwards != 1) then do
7) 20:00:00.854 -> CTA2: void stuck(int dur == 12000
8) 20:00:00.894 -> CTA27: void spinR(int dur == 12000
9) 20:00:12.860 -> CTA2: void stuck(int dur == 12000
10) 20:00:12.900 -> CTA4: void stuck(int dur == 1600
...
Редактировать, чтобы добавить: Версия Arduino 1.8.13, Win7, протестирована на Nano Atmega168PA и Mega2560
@lsbyte, 👍2
Обсуждение1 ответ
Ваша пустота застряла() { ... }
, который вызывается внутри первого if (timeisup == true && goingForwards == 1) { ... }
может установить complexManoeuvre
в ненулевое значение, прежде чем будет достигнуто второе if (timeisup == true && goingForwards != 1) { ... }
(тот, у которого "Что за?!").
точно Serial.print(F("CTA26: ")); complexManoeuvre = 2; recerse(dur);
, @Juraj
Но, если я не ошибаюсь, это нужно сделать для того, чтобы процесс вернулся к stuck(), чтобы продолжить через переключатель (прогресс)., @lsbyte
Это не совсем "может установить", он установит его равным 2, @KIIV
Измените инструкции if() на вторую версию, и все будет работать так, как должно. Но... вот чего я не понимаю., @lsbyte
@lsbyte Возможно, ему нужно это сделать, но после завершения заблокированного вызова он продолжит обработку команд после этого вызова. Это означает, что он выходит из первого вложенного блока if {}, и угадайте что, другой вложенный if находится сразу после этого первого., @KIIV
Но разве прогресс не должен увеличиваться только один раз каждый раз, когда процесс посещает stuck()? Я не понимаю, как изменение операторов if() в цикле может повлиять на поведение переключателя (прогресс), @lsbyte
@lsbyte Вы делаете в значительной степени это int a = 0; if (a == 0) { a = 2; } if (a != 0) { Serial.println("но почему?"); }
и вы спрашиваете, почему a не равно нулю, после вы изменили его на 2. У `застрявшего" есть "побочные эффекты", и один из них - изменение "Сложного маневра"., @KIIV
Давайте [продолжим это обсуждение в чате] (https://chat.stackexchange.com/rooms/115843/discussion-between-lsbyte-and-kiiv )., @lsbyte
- C++ против языка Arduino?
- Как использовать SPI на Arduino?
- Какие накладные расходы и другие соображения существуют при использовании структуры по сравнению с классом?
- Ошибка: expected unqualified-id before 'if'
- Что лучше использовать: #define или const int для констант?
- Функции со строковыми параметрами
- Библиотека DHT.h не импортируется
- ошибка: ожидаемое первичное выражение перед токеном ','
if(timeisup == true)
эквивалентноif(true == true)
, что является избыточным...if (timeisup)
- это то же самое, @jsotola