Forse questo non è il posto giusto ma ci provo lo stesso:
dovrei salvare in una variabile il valore ricavato da un analizzatore di rete elettrica che comunica in protocollo RS 485 Modbus RTU.
Questo protocollo consiste in richieste al dispositivo tramite frame e risposte dallo stesso con altro frame dove si possono trovare i valori richiesti.
Questo è il punto:
i dati utilizzati come risposta sono in formato floating point 32bit IEEE
Per capire un po' questo formato ho trovato un software che crea le stringhe e le invia registrandone le risposte dallo slave.
Allego le schermate dell'applicazione per comprendere:
Facendo un'interrogazione dei registri interessati (2, sempre adiacenti) la stringa di risposta è quella evidenziata in nero nella prossima schermata
I valori utili per il dato da estrapolare sono questi [43] [61] [B3] [33]
Il formato selezionato nella immagine mi restituisce il valore corretto della lettura (in questo caso in volt)
Alla fine di questa pappardella vi chiedo: esiste qualche modo/metodo/libreria che mi converta questi 4 numeri esadecimali in un valore rispondente al valore da ottenere?
Mi scuso per l'esposizione forse non estremamente tecnica ma l'argomento è parecchio complicato...
Grazie
FANTASTICO.... però però ora devi spiegarmi passo passo (abbi pazienza ma fare le cose a copiaincolla senza capire non mi piace) le varie righe di codice... sono poche
Una union è come una struct, una struttura che contiene altre "parti" o variabili.
Nel nostro caso dentro la MB_float ci sono 5 parti, f e poi s.b1, s.b2, s.b3, s.b4
Essendo una union f e le quattro parti di s (ovvero b1-b4) si "sovrappongono".
Scrivendo nell'ordine giusto le 4 parti (byte) che compongono il float, leggendo la parte f hai il numero con virgole.
Qui io ho scritto i valori (come esadecimali) che tu hai letto con il programma:
mix.s.b4=0x43; // ovvero 67 decimale
mix.s.b3=0x61;
mix.s.b2=0xB3;
mix.s.b1=0x33;
Serial.println(mix.f);
E poi stampo la parte f della variabile per avere il numero con virgole.
Logicamente tu dovrai leggere i 4 byte dal Bus e poi scriverli dentro a mix.s.b1 fino a mix.s.b4 e NELL'ORDINE giusto.
Nella union mix_t non capisco il concetto di "unire" la variabile float f con struct (che mi pare di aver capito essere un raggruppamento di dati che possono essere anche di diverso tipo)
Ho letto inoltre che volendo su può omettere nella struct l'identificatore s
L' hai aggiunta tu ma non serve vero, per il calcolo?
Ho provato ad invertire in Serial.println(mix.f)mix con f per curiosità ma mi viene reso un errore in fase di compilazione: la sequenza corretta fa parte del costrutto di Serial.print() o cosa?
Senza offera @franchelli, ma una struct o union è spiegata bene in un manuale di C.
Ti ho postato un link ad un sito che da una spiegazione di struct e union, con esempi.
In un forum mi viene difficile darti tutte le spiegazioni della struct, cerca su quel link o su internet in generale.
Come detto da @vbextreme, quella union facilita quello che puoi fare con il calcolo da lui indicato.
La seconda parte del codice da me postato non serve, è solo la riprova che un float=225,70 spezzato in 4 byte da i valori che avevi postato
Il nome "s" della struct lo puoi cambiare ma non evitare. Le parti della union che coincidono in memoria sono f ed s ovvero 4 byte in memoria.
f | . . . .| 4 byte
s |b1|b2|b3|b4| 4 byte che sono le 4 parti del float
In una struct o union alle varie parti (campi) si accede con variabile.campo nel nostro caso mix.f oppure mix.s.b3
Non puoi invertire quell'ordine.
nid69ita:
Senza offera @franchelli, ma una struct o union è spiegata bene in un manuale di C.
Ti ho postato un link ad un sito che da una spiegazione di struct e union, con esempi.
In un forum mi viene difficile darti tutte le spiegazioni della struct, cerca su quel link o su internet in generale.
CUT
Hai assolutamente ragione e sei stato fin troppo disponibile... Il sito indicato ed anche qualche altro, li ho letti e riletti ma i concetti alle volte sono non proprio elementari.
Mi hai comunque chiarito molti aspetti oscuri, grazie.