проблема с миганием светодиода

я сделал схему измерения расстояния с разными светодиодами для разных диапазонов расстояний

#define trigPin 13
#define echoPin 12
#define BPin 7
#define piezoPin 9
#define RPin 4
#define GPin 8

void setup() {
  Serial.begin (9600);
  pinMode(trigPin, OUTPUT);
  pinMode(echoPin, INPUT);
  pinMode(BPin, OUTPUT);
  pinMode(piezoPin, OUTPUT);
  pinMode(RPin, OUTPUT);
  pinMode(GPin, OUTPUT);
}

void loop() {
  long duration, distance;
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  duration = pulseIn(echoPin, HIGH);
  distance = (duration / 2) / 29.1;

  if (distance >= 200 || distance <= 0) {
    Serial.println("Out of range");
  }
  else {
    Serial.print(distance);
    Serial.println(" cm");
  }
  delay(1000);
  {
    if (distance <= 25 || distance <= 0) {
      digitalWrite(RPin, HIGH);
    }
    else {
      digitalWrite(RPin, LOW);
    }
  }

  {
    if (distance >= 25 && distance <= 50) {
      digitalWrite(GPin, HIGH);
    }
    else {
      digitalWrite(GPin, LOW);
    }

    {
      if (distance >= 50 && distance <= 75) {
        digitalWrite(GPin, HIGH);
      }
      else {
        digitalWrite(BPin, LOW);
      }

      {
        if (distance >= 75 && distance <= 100) {
          digitalWrite(BPin, HIGH);
        }
        else {
          digitalWrite(GPin, LOW);
          {
            {
              if (distance >= 100 && distance <= 200) {
                digitalWrite(piezoPin, HIGH);
              }
              else {
                digitalWrite(piezoPin, LOW);
              }
            }
          }
        }
      }
    }
  }
}

все работает нормально, кроме Gpin, он мигает, пожалуйста, помогите мне я также загружаю ссылку для загрузки моего файла .ino связь; https://www.datafilehost.com/d/e19b35d5

, 👍-1

Обсуждение

Сначала выровняйте свой код (поместите { и } друг под другом, которые связаны друг с другом, а также удалите ненужные { и } (например, вокруг операторов if). Также не делайте отступ, когда он не нужен (например, настройки режима вывода)., @Michel Keijzers

Я отформатировал ваш код, и ваша логика чрезвычайно запутана и, я подозреваю, также неверна в нескольких местах. Я насчитал как минимум 5 ненужных скобок и несовместимую структуру if/else. Кроме того, если что-то меньше 25, это уже меньше 0., @Filip Franik

Думаю, это должно быть if(distance blabla) digitalWrite(pinX,HIGH); else digitalWrite(pinX,LOW); (у вас разные выводы в случае if/else). Также два светодиода будут гореть, когда distance==50, distance==75 или distance==100, что я считаю ошибкой., @Sim Son


1 ответ


0

Это ваш код без лишних скобок:

#define trigPin 13
#define echoPin 12
#define BPin 7
#define piezoPin 9
#define RPin 4
#define GPin 8

void setup() {
  Serial.begin (9600);
  pinMode(trigPin, OUTPUT);
  pinMode(echoPin, INPUT);
  pinMode(BPin, OUTPUT);
  pinMode(piezoPin, OUTPUT);
  pinMode(RPin, OUTPUT);
  pinMode(GPin, OUTPUT);
}

void loop() {
  long duration, distance;
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  duration = pulseIn(echoPin, HIGH);
  distance = (duration / 2) / 29.1;

  if (distance >= 200 || distance <= 0) {
    Serial.println("Out of range");
  }
  else {
    Serial.print(distance);
    Serial.println(" cm");
  }
  delay(1000);

  if (distance <= 25 || distance <= 0) {
    digitalWrite(RPin, HIGH);
  }
  else {
    digitalWrite(RPin, LOW);
  }

  if (distance >= 25 && distance <= 50) {
    digitalWrite(GPin, HIGH);
  }
  else {
    digitalWrite(GPin, LOW);
  }

  if (distance >= 50 && distance <= 75) {
    digitalWrite(GPin, HIGH);
  }
  else {
    digitalWrite(BPin, LOW);
  }

  if (distance >= 75 && distance <= 100) {
    digitalWrite(BPin, HIGH);
  }
  else {
    digitalWrite(GPin, LOW);
    if (distance >= 100 && distance <= 200) {
      digitalWrite(piezoPin, HIGH);
    }
    else {
      digitalWrite(piezoPin, LOW);
    }
  }
}

Используя тернарный оператор, вы можете упростить запись операторов if:

#define trigPin 13
#define echoPin 12
#define BPin 7
#define piezoPin 9
#define RPin 4
#define GPin 8

void setup() {
  Serial.begin (9600);
  pinMode(trigPin, OUTPUT);
  pinMode(echoPin, INPUT);
  pinMode(BPin, OUTPUT);
  pinMode(piezoPin, OUTPUT);
  pinMode(RPin, OUTPUT);
  pinMode(GPin, OUTPUT);
}

void loop() {
  long duration, distance;
  digitalWrite(trigPin, LOW);
  delayMicroseconds(2);
  digitalWrite(trigPin, HIGH);
  delayMicroseconds(10);
  digitalWrite(trigPin, LOW);
  duration = pulseIn(echoPin, HIGH);
  distance = (duration / 2) / 29.1;

  if (distance >= 200 || distance <= 0) {
    Serial.println("Out of range");
  }
  else {
    Serial.print(distance);
    Serial.println(" cm");
  }
  delay(1000);

  digitalWrite(RPin, (distance <= 25 || distance <= 0) ? HIGH : LOW);
  digitalWrite(GPin, (distance >= 25 && distance <= 50) ? HIGH : LOW);

  if (distance >= 50 && distance <= 75) {
    digitalWrite(GPin, HIGH);
  }
  else {
    digitalWrite(BPin, LOW);
  }

  if (distance >= 75 && distance <= 100) {
    digitalWrite(BPin, HIGH);
  }
  else {
    digitalWrite(GPin, LOW);
    digitalWrite(piezoPin, (distance >= 100 && distance <= 200) ? HIGH : LOW);
  }
}

Несколько замечаний для размышления, которые помогут вам решить ваш набросок (и являются причиной того, что ваш GPin может мигать):

  1. Часть строки (distance <= 25 || Distance <= 0) может быть переписана в (distance <= 25), поскольку если значение меньше/равно 0, оно автоматически меньше/равно 25.

  2. В зависимости от того, какое условие вы устанавливаете для одного вывода – ВЫСОКОЕ или для другого вывода – НИЗКОЕ, я ожидаю, что изменятся оба вывода или один и тот же вывод. Но я не знаю ваших требований.

  3. Значения "край" (например, 25, 50, 75) попадают в несколько условий, возможно, вы захотите исключить конечное ребро. Это своего рода рекомендация включать начало и исключать конец, например . if (расстояние >= 50) && (расстояние < 75).

В вашем случае лучше всего проверять расстояние следующим образом:

if (distance < 0)
{
   ...
} 
else if (distance < 25)
{ 
   // 0 <= расстояние < 25)
   ...
}
else if (distance < 50)
{
   // 25 <= расстояние < 50)
}
... 

или наоборот:

digitalWrite(GPin, 'condition in which GPin should be on' ? HIGH : LOW);
digitalWrite(BPin, 'condition in which BPin should be on' ? HIGH : LOW);

например, если вы хотите, чтобы GPin был включен в диапазоне от 0 до 25:

digitalWrite(GPin, ((distance >=0) && (distance < 25) ? HIGH : LOW);
,

Боюсь, ваш вывод по пункту 1. неверен. Первая строка в порядке. Но если значение меньше или равно 25, оно автоматически не меньше 0. Например, значение 25 меньше или равно 25, но больше 0. Но верно и другое направление. Я знаю, я считаю горох, это мое хобби ;-)., @Peter Paul Kiefer

@PeterPaulKiefer Думаю, я прав. Если расстояние меньше 0, оно всегда меньше 25, поэтому подвыражение Distance < 0 не нужно, так как диапазон (-infinit,0) находится в пределах диапазона (-infinit, 25). Если бы оператор был &&, вы были бы правы., @Michel Keijzers

Да, формула, которую вы вывели, верна, но вы написали «поскольку, если значение меньше/равно 25, оно автоматически меньше/равно 0». И это неправильно., @Peter Paul Kiefer

Извините, возможно, слово «заключение» вас раздражает, но я не являюсь носителем английского языка. Возможно, я неправильно использовал его., @Peter Paul Kiefer

@PeterPaulKiefer Не нужно извиняться, я просто полностью упустил вашу мысль, я был сосредоточен на формуле, а не на тексте. И вы были правы, поэтому я исправил ответ. Вы меня ничуть не разозлили, я просто переврал ваш текст (я тоже не носитель языка). Спасибо за ваше улучшение, и я соответствующим образом адаптировал свой ответ., @Michel Keijzers