Передача float

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
Давайте вспомним, что язык в arduino IDE отличается от канонического С++, поэтому строгие требования С++ к нему можно применять а можно и нет.
Ошибаетесь. Внутре arduino IDE у нее неонка использует компилятор gcc, поэтому все там применимо. Что язык позволяет некоторые вольности до поры до времени, это цена эффективности и гибкости, но если не хотите тратить очень много времени на отлавливания тяжелых багов, то правила лучше соблюдать. Например в вашем случае, это будет просто:
Код:
float f1 = 123.45678;
int32_t d1 = 0;
assert( sizeof( int32_t ) == sizeof( float ) );
memcpy( &d1, &f1, sizeof( int32_t ) );
Ничего сложного, правда?
Если использовать более строгую среду или более строгую компиляцию могут посыпаться ошибки и предупреждения.
Вот тут еще одно характерное заблуждение новичков - если при компилировании "ошибки и предупреждения не сыпятся" значит программа верна. К сожалению это не так, хотя бы по простой причине - их можно подавить. На практике еще хуже - даже если программа дает предсказуемый результат, это еще не значит, что она верна. Такова цена эффективности.
 

Старик Похабыч

★★★★★★★
14 Авг 2019
4,271
1,303
Москва
Сама по себе среда настроена на начинающих пользователей, ибо непомерная (со стороны начинающих) проверка отпугнет их с рынка. Но и никто не запрещает включить все предупреждения. Это так.
 

poty

★★★★★★✩
19 Фев 2020
3,262
949
@rGlory, дайте ссылку на стандарт, который это запрещает. Тогда разговор будет предметным. В настоящее время - больше предположений без обоснований.
 

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
И что интересно программисты сишники в зависимости от текущего настроения все эти "хаки" и "трюки" могут заносить языку то в + то в -
Злоупотребление хаками - это частая болезнь новичков. Как известно на любом языке программирования можно написать программу на Фортране. Если вы посмотрите на код опытного программиста, он как раз не будет злоупотреблять хаками и такой код читаемый и простой. На самом деле писать простой и читаемый код, это гораздо сложнее, чем писать "спагетти" код. (хотя это довольно очевидно, иначе начинающие этим бы не грешили)
 

Старик Похабыч

★★★★★★★
14 Авг 2019
4,271
1,303
Москва
Простое и верное решение указал Эдуар, и я с этим полностью согласен. Зачем дублировать ответ ? И да, сам я бы не стал так делать , скорее использовал бы union в подобной ситуации, если бы посчитал, что передача как массив байт не эффективна.
Но т..к Вы не видели мой код , а мне не очень интересно смотреть Ваш. оставим кто тут новичок. Если что, у меня опыт программирования больше чем многие живут.
 

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
@rGlory, дайте ссылку на стандарт, который это запрещает. Тогда разговор будет предметным. В настоящее время - больше предположений без обоснований.
Да без проблем: http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2017/n4713.pdf
11 If a program attempts to access the stored value of an object through a glvalue of other than one of the following types the behavior is undefined:63
(11.1) — the dynamic type of the object,
(11.2) — a cv-qualified version of the dynamic type of the object,
(11.3) — a type similar (as defined in 7.5) to the dynamic type of the object,
(11.4) — a type that is the signed or unsigned type corresponding to the dynamic type of the object,
(11.5) — a type that is the signed or unsigned type corresponding to a cv-qualified version of the dynamic type of the object,
(11.6) — an aggregate or union type that includes one of the aforementioned types among its elements or nonstatic data members (including, recursively, an element or non-static data member of a subaggregate or contained union),
(11.7) — a type that is a (possibly cv-qualified) base class type of the dynamic type of the object,
(11.8) — a char, unsigned char, or std::byte type.
Если что, у меня опыт программирования больше чем многие живут.
Но оффенсе, но ваши попытки привести указатель на float к указателю на int32_t прямо говорят, что опыта на С++ у вас мало. Кроме того мой пассаж был не про вас, а про некоторых программистов на С или С++, которые любят использовать хаки, потому, что это круто. С опытом это обычно проходит. Хотя бывают исключения.
И да, сам я бы не стал так делать , скорее использовал бы union в подобной ситуации, если бы посчитал, что передача как массив байт не эффективна.
Проблема в том, что и подход с union нелегален в С++ ;)
Но здесь скорее всего проблем не будет, маловероятно, что разработчики компиялтора сломают совместимость с С просто ради фана.
 
Изменено:
  • Лойс +1
Реакции: kDn

kDn

★★★★★✩✩
18 Ноя 2019
1,103
437
Проблема в том, что и подход с union нелегален в С++ ;)
Но здесь скорее всего проблем не будет, маловероятно, что разработчики компиялтора сломают совместимость с С просто ради фана.
Я, если что, понял. Не тупой :) . К вашему замечанию у меня нет возражений. Некоторый же пофигизм в моем случае вызван устаревшими знаниями (я вовсе не так сильно владею текущими стандартами, а мой сертификат двадцатилетней давности несколько устарел) и по большей мере отсутствием достаточного уровня усидчивости и вдумчивости для проведения рефакторинга кода. Но вас, я буду рад видеть в виде ревьювера или как активного участника, если возникнет желание вдруг поработать совместно над каким-нибудь опенсорсом.
 

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
Но вас, я буду рад видеть в виде ревьювера или как активного участника, если возникнет желание вдруг поработать совместно над каким-нибудь опенсорсом.
Взаимно. (y)
Не хотел никого обидеть или унизить. Не знать что-то и быть новичком в какой-то области, это нормально и полезно признавать это, тогда ты открыт для новых знаний. Просто к сожалению у С++ есть "плохая" слава языка, на котором практически невозможно написать корректные программы, в этом виновата конечно и сложность языка, но в основном отсутсвие самодисциплины у разработчиков. А уж утечки памяти, это вообще притча во языцах. Но на самом деле большинста из этих проблем можно избежать, достаточно прививать в себе полезные привычки и пытаться избавиться от вредных.
 
  • Лойс +1
Реакции: kDn

kDn

★★★★★✩✩
18 Ноя 2019
1,103
437
@rGlory, я лет десять назад сказал "никогда больше не буду писать на плюсах", а год назад решил глянуть, а что же там сейчас в мире контроллеров... ну и понеслось все снова ;) . Ну, а то что я не знаю плюсы на достаточно хорошем уровне меня даже не расстраивает нисколько, т.к. я прекрасно знаю, что значительное количество людей считающих, что знают его достаточно хорошо - занимаются самообманом ;) .

Так что если выдастся случай ткнуть меня носом в стандарт - обязательно воспользуйтесь этим, буду крайне признателен. Об обидах вообще не идет речь, меня попросту невозможно обидеть.
 
  • Лойс +1
Реакции: Старик Похабыч

Александр Симонов

★★★★✩✩✩
2 Авг 2018
727
208

SO_OOF

✩✩✩✩✩✩✩
7 Июн 2021
14
1
Уважаемые пользователи. Тут вопрос возник. А если esp-01 что-нибудь напишет в serial, она потом не прочитает это?
Просто мне нужен обмен именно arduino отправила, esp прочитала и наоборот?
 

Александр Симонов

★★★★✩✩✩
2 Авг 2018
727
208
@SO_OOF, да, организовать обмен "arduino отправила, esp приняла (и наоборот)" можно. Делается или через SoftwareSerial или через Serial. В последнем случае надо будет отключать esp от ардуино во время прошивки ардуино (и наоборот), чтобы они не гадили друг другу в сериал и не мешали прошивке
 

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
В последнем случае надо будет отключать esp от ардуино во время прошивки ардуино (и наоборот), чтобы они не гадили друг другу в сериал и не мешали прошивке
По моему проще будет их по SPI соединить, а не по UART в таком случае...
 

bort707

★★★★★★✩
21 Сен 2020
3,069
916
По моему проще будет их по SPI соединить, а не по UART в таком случае...
проще будет отказаться от ардуино. ТС стоит подумать, а не справится ли один ЕСП там, где он планирует связку Есп + ардуино ЕСП сам по себе куда более мощный МК
 

Старик Похабыч

★★★★★★★
14 Авг 2019
4,271
1,303
Москва
Если есть полностью готовый проект на арудино, а автор задает такие вопросы, то переписать все на esp точно не проще.
 
  • Лойс +1
Реакции: Nikanor

bort707

★★★★★★✩
21 Сен 2020
3,069
916
Если есть полностью готовый проект на арудино, а автор задает такие вопросы, то переписать все на esp точно не проще.
если автор задает вопросы уровня "как передать данные через сериал" - то ему никакой вариант не будет "проще". Похорошему ему еще рано делать проекты, для начала надо в базовых вещах разобраться
 

SO_OOF

✩✩✩✩✩✩✩
7 Июн 2021
14
1
Да я понял, что esp мощнее. Но у меня esp-01 у него мало контактов. А покупать другой и все переписывать под него, уже не особо хочется. У меня ардуинка выступает просто как чтец данных с датчиков и передает все на esp, а та уже пересылает данные на сервак. У меня все работает отлично. Могу скинуть код кому интересно. Но есть одно но, имя вайфай точки, пароль и ip сервера жестко прописаны. И если нужно что-то менять. То приходится каждый раз заливать прошивку на esp. Никто не знает, а есть ли способ, как-то делать это с браузера? Я нашел библу wifimanager она позволяет менять точку доступа, но вот ip сервера, я не нашел.

@bort707, Я просто первый раз работаю с ардуино. До этого в универе работал только с обычной атмегой в avr studio. И там не было виртуального ком порта, как в ардуино ide поэтому мне немного сложно это понять

Вот код ардуинки

C++:
#include <DHT.h>
#include <Wire.h>
#include <Adafruit_CCS811.h>
#include <ArduinoJson.h>

#define DHTPIN 2
#define DHTTYPE DHT22
#define ADDRESS 0x5B

unsigned long last_time;
float humidity, temperature;
int CO2, TVOC;

const size_t CAPACITY = JSON_OBJECT_SIZE(4); //выделяем память для документа
StaticJsonDocument<CAPACITY> doc;
JsonObject object = doc.to<JsonObject>(); //создаем объект

DHT dht(DHTPIN, DHTTYPE); //Инициация датчика
Adafruit_CCS811 ccs; //Инициация датчика

void setup() {
  Serial.begin(115200);
  dht.begin();
  ccs.begin(ADDRESS);
}

void loop() {
  if (millis() - last_time >= 2000) {
    last_time = millis();
    get_dht_sensor(humidity, temperature);
    get_ccs_sensor(CO2, TVOC);
    sending_data(humidity, temperature, CO2, TVOC);
  }
}

float get_dht_sensor(float &out_humidity, float &out_temperature) {
  out_humidity = dht.readHumidity(); //Измеряем влажность
  out_temperature = dht.readTemperature(); //Измеряем температуру
  if (isnan(humidity) || isnan(temperature)) {
    return 0;
  }
}

int get_ccs_sensor(int &out_CO2, int &out_TVOC) {
  if(ccs.available() && !ccs.readData()) {
    out_CO2 = ccs.geteCO2(); //Измеряем CO2
    out_TVOC = ccs.getTVOC(); //Измеряем TVOC
  }
  else {
    return 0;
  }
}

void sending_data(float humidity, float temperature, int CO2, int TVOC) {
  int new_humidity = round(humidity * 100);
  int new_temperature = round(temperature * 100);

  object["humidity"] = new_humidity;
  object["temperature"] = new_temperature;
  object["CO2"] = CO2;
  object["TVOC"] = TVOC;

  serializeJson(doc, Serial); //сериализуем объект и отправляем результат в Serial
}

код есп

C++:
#include <ESP8266WiFi.h>
#include <WiFiClient.h>
#include <WiFiUdp.h>

const char* ssid = "***";
const char* password = "***;

unsigned long last_time;
String temp;
char json_string[200];
const int port = 8888;

IPAddress server_ip(192,168,1,65);
WiFiUDP Udp;

void setup() {
  Serial.begin(115200);
  WiFi.begin(ssid, password); //Инициализация соединения Wi-Fi
  while (WiFi.status() != WL_CONNECTED) { //ожидание соединения
  delay(500);
  }
}

void loop() {
  if (millis() - last_time >= 2000) {
    last_time = millis();
    data_reception();
    udp_send();
  }
}

void data_reception() {
  temp = "";
  while (Serial.available() > 0) {
    temp += char(Serial.read()); //читаем данные переданные arduino
  }
  temp.toCharArray(json_string, 200);
}

void udp_send() { //отправляем UDP на сервер
  Udp.beginPacket(server_ip, port);
  Udp.write(json_string);
  Udp.endPacket();
}
 
  • Лойс +1
Реакции: Старик Похабыч

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
Я нашел библу wifimanager она позволяет менять точку доступа, но вот ip сервера, я не нашел.
Получайте адресс динамически, по DHCP, не нужно будет ничего менять в прошивке.
Вот код ардуинки
Ну вы сейчас передаете умноженный на 100. В чем проблема? Вам не хватает точности?

Кстати, а что json не умеет работать с float? :oops:

Посмотрел доку, поддерживает он float, в чем дело то, почему вы не передаете напрямую? Из-за чего весь сыр бор?
 
Изменено:

SO_OOF

✩✩✩✩✩✩✩
7 Июн 2021
14
1
Получайте адресс динамически, по DHCP, не нужно будет ничего менять в прошивке.
Так адрес сервера не может быть динамически задан. Это же не логично будет

Кстати, а что json не умеет работать с float? :oops:
Возможно может, просто * на 100 это давно делалось, и скорее всего уже не нужно)
 

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
Так адрес сервера не может быть динамически задан. Это же не логично будет
Еще как может, и ничего нелогичного здесь нет. В конфигурации DHCP прописываете фиксированный адрес для MAC адресса вашей ESP, и все и адрес будет постоянный, и можно поменять, если нужно. И в другой сети он получит другой адрес.

Возможно может, просто * на 100 это давно делалось, и скорее всего уже не нужно)
А так вы проблему решили кардинально, и передаете данные через json? Предупреждать надо.
 
Изменено:

SO_OOF

✩✩✩✩✩✩✩
7 Июн 2021
14
1
Еще как может, и ничего нелогичного здесь нет. В конфигурации DHCP прописываете фиксированный адрес для MAC адресса вашей ESP, и все и адрес будет постоянный, и можно поменять, если нужно. И в другой сети он получит другой адрес.
Так сервер у меня поднят на компе. esp передает инфу компу. А комп может иметь другой ip
 

rGlory

★✩✩✩✩✩✩
11 Май 2021
200
20
ак сервер у меня поднят на компе. esp передает инфу компу. А комп может иметь другой ip
А, вы про этот ip. Что-то я туплю с утра.
Тут есть варианты -
  • посылать пакет всем броадкастом
  • посылать пакет всем желающим мультикастом
  • использовать DNS - в прошивке использовать имя сервера, а не его адрес
  • ждать определенный пакет на определенный порт, после этого начинать посылать тому, кто тот пакет прислал
Хватит?