Go Down

Topic: Semplice rete neurale per Arduino 2 (Read 15804 times) previous topic - next topic

zoomx

Si, bello che funziona anche su altro hardware.

Prima di postare però direi di aspettare l'implementazione della lettura dei pesi. Però qui si pone un problemino. Da dove si leggono? Dalla EEPROM (ma se non ricordo male sulla DUE non c'è)? Da SD? Memoria I2C?

Ma non è possibile utilizzare in qualche modo la Flash rimasta invece della EEPROM?

Nessuno ha fatto la prova sulla DUE? Mi pare che questa DUE non sta avendo successo o sbaglio?

yoshi93

#121
May 23, 2013, 04:13 pm Last Edit: May 23, 2013, 04:18 pm by yoshi93 Reason: 1
Io pensavo da pc sulle prime con la porta usb host così non si resetta nulla quando la colleghi. Alle SD e alle memorie I2C penserò in un secondo momento. Si potrebbe mandare l'ARM in modalità autoprogrammazione per accedere alla flash però è pericoloso, basta un errore e devi ricompilare tutto. Ora che ci penso sarebbe interessante poter inviare i pesi tramite internet.

P.S. La due è una scheda particolare che non è nata per i principianti. Credo sia per questo che non sta riscuotendo un successo strepitoso. Essendo poi open source ed abbastanza conosciuta ci sono stati molti cloni già da subito percui poi gli acquirenti si disperdono.

yoshi93

Aggiornamento:
Posto i moduli della rete con una prima bozza dei moduli per il caricamento/salvataggio dati.

Il sistema di trasferimento si basa sull'invio degli int/float come sequnze di 4 byte in modo da eliminare eventuali problemi di parseInt() e parseFloat() ed avere lo stesso tempo di trasferimento per ogni numero.

Chiedo consigli su come fare il tool lato pc e commenti/suggerimenti per il codice considerando che non ho mai usato la Serial in questo modo.

zoomx

Non mi era mai capitato di dover trasmettere dei valori a più byte. Leggendo la guida di riferimento e il tuo codice mi è anche venuto in mente della possibile causa del fallimento dell'emulatore.
Gli int nella DUE sono a 4 byte mentre nella UNO a 2 byte. Mi chiedo il perché di tale differenza visto che esiste il long che su entrambe è a 4 byte. Se si tratta di una particolarità del micro utilizzato mi chiedo perché non sia stata risolta con il compilatore.

A parte questo mi pare funzioni. Io avrei lavorato direttamente con i puntatori, tenendo conto delle architetture BigEndian e LittleEndian(Intel LittleEndian, gli ARM attuali dovrebbero essere invece BigEndian), così tutti i valori sono degli array di 4 byte e la funzione per spedire o leggere un valore è identica. In effetti non so se il tuo codice è affetto dalla questione Big o Little Endian.

Per gli interi si potrebbe usare anche la rappresentazione in ASCII. Bisognerebbe cambiare la routine di lettura, che si dovrebbe aspettare un terminatore ma rimarrebbe sempre il problema per i float. Adesso capisco perché avevi lasciato questa parte per dopo.

Una volta che è definito il protocollo di scambio, il programma su PC potrebbe essere fatto in Java, che è abbastanza universale. Io però non lo conosco. Altrimenti ce ne vorrebbe uno per ogni sistema operativo perché perfino in C cambia la modalità di accesso alla seriale.

Devo cercare un vecchio programma che avevo scritto anni fa...

astrobeed


Gli int nella DUE sono a 4 byte mentre nella UNO a 2 byte. Mi chiedo il perché di tale differenza visto che esiste il long che su entrambe è a 4 byte. Se si tratta di una particolarità del micro utilizzato mi chiedo perché non sia stata risolta con il compilatore.


Perché con i processori a 32 bit l'int è lungo quanto la word, per gli interi a 16 bit devi usare il tipo "short int" oppure "short unsigned int".

zoomx

Ma perché cambiare gli int visto che già esistevano i long e creare lo short int?

Voglio dire, se il micro è a 32 bit e lavora meglio con unità di 4 byte perché non lasciare questo compito al compilatore?

Non è un rimprovero al compilatore Arduino, so che nel passaggio dai 16 ai 32 bit è successo questo per molti, forse tutti i compilatori.

Io non vedo problemi in un micro a 32 bit che prende una variabile di 16 bit e la sbatte in un registro da 32, fa le operazioni che deve fare e risbatte gli ultimi 2 byte daccapo in memoria, tenendo conto degli overflow.
Se ho degli hoverhead a lavorare a 16 bit, ne sono cosciente, oppure lo leggo nella documentazione, e cambio il codice passando dagli int ai long. Su PC in effetti ho fatto così.

Io penso che un motivo ci sarà stato, lo spero!, e sarà stato un motivo di efficienza, ma mi chiedo quale sia.

La conseguenza è proprio che il codice non funziona in maniera identica. E che succede adesso con i processori a 64bit?

lesto

credo che 32 bit si riferisce al bus, non è detto che i registri poi lo siano.. o erro?

quindi magari la ALU lavora a 16bit, da quì la scelta
sei nuovo? non sai da dove partire? leggi qui: http://playground.arduino.cc/Italiano/Newbie

leo72

@zoomx:
Non c'entra Arduino, il compilatore mica lo hanno scritto loro  ;)

@lesto:
i registri del SAM3X sono a 32 bit.

leo72

Ho spostato la discussione qui in Megatopic, credo che la cosa sia abbastanza matura ed interessante per poterci stare senza problemi  ;)

astrobeed


Ma perché cambiare gli int visto che già esistevano i long e creare lo short int?


Non è stato cambiato assolutamente nulla, è il C che prevede questa cosa come standard del linguaggio, su processori con word pari o minore di 16 bit l'int = short int è di 16 bit, su processori con word maggiore di 16 bit l'int è 32 bit e per i 16 bit si devono usare gli short int, ti faccio presente che anche su Arduino UNO puoi scrivere "short int" se vuoi mantenere la compatibilità per un eventuale porting verso un 32 bit.
Per ovviare a questa possibile ambiguità, col tempo, al C standard sono state aggiunti degli alias standard per i tipi di dato, p.e. uint8_t (= unsigned char) oppure uint16_t (= unsigned short int), che specificano chiaramente oltre al tipo di dato anche la sua dimensione.

astrobeed


credo che 32 bit si riferisce al bus, non è detto che i registri poi lo siano.. o erro?


No la word è sempre riferita alla quantità di bit che il processore può trattare con una singola operazione, ovvero la dimensioni dei suoi registri macchina, invece il bus può benissimo essere sia minore che maggiore della word, dipende dall'architettura interna del micro.

zoomx


Per ovviare a questa possibile ambiguità, col tempo, al C standard sono state aggiunti degli alias standard per i tipi di dato, p.e. uint8_t (= unsigned char) oppure uint16_t (= unsigned short int), che specificano chiaramente oltre al tipo di dato anche la sua dimensione.

astrobeed,
io non conosco ancora il C ma la tua risposta mi ha illuminato! L'aggiunta degli alias conferma che, forse, la scelta di cambiare la dimensione degli int non è stata, ancora forse, intelligente. Avevo già visto questi alias in alcune librerie e programmi e adesso, grazie a te, ho capito che sono alias e perché sono stati usati. Penso che li userò anche io in modo da non avere ambiguità.
Ancora grazie!

astrobeed


io non conosco ancora il C ma la tua risposta mi ha illuminato! L'aggiunta degli alias conferma che, forse, la scelta di cambiare la dimensione degli int non è stata, ancora forse, intelligente.


Devi anche pensare a quanti anni ha il C e a quali computer esistevano all'epoca, col tempo, rispetto alla prima stesura del linguaggio, ci sono state delle revisioni ed ecco perché si dovrebbe sempre parlare di C ANSI99, o ISO C99, per evitare ambiguità con le predenti versioni.
Da notare che i nomi per gli alias dei tipi dato standard, che rimangono sempre char, int, etc, possono differire leggermente nella sintassi a seconda del compilatore o, in certi casi, non essere presenti, capita facilmente con compilatori C non ANSI per mcu a 8 bit, però è facile ovviare con un file .h contenente le relative #define.

yoshi93

#133
May 24, 2013, 05:22 pm Last Edit: Jun 01, 2013, 12:14 am by yoshi93 Reason: 1
Megatopic che onore  8).

Adesso capisco perché avevi lasciato questa parte per dopo.


Vedi che c'è sempre un perchè  ;)? Per quanto riguarda la questione delle diverse lunghezze dei dati secondo me è meglio usare gli int a 32bit sulla DUE. Primo perchè è lo standard come ha detto astro (e lo standard è legge) secondo perchè così si usa tutta la potenzialità del processore.


Per gli interi si potrebbe usare anche la rappresentazione in ASCII

No, meglio non usare ASCII e trattare tutto come bytes senza scomodare i caratteri.

EDIT:
Il programma di gestione sarà fatto in python (versione 3) poichè per il C++ non ho trovato niente di soddisfacente e userà la libreria pySerial. Come interfaccia grafica userò Tkinter che è il pacchetto grafico di default di python evitando così inutili grattacapi.


Rosik

Librerie molto utili, mi hanno aiutato molto per portare a compimento il mio progetto di maturità ovvero un controllo qualità dei pezzi per dividere pezzi buoni da pezzi da scartare riuscendo a generalizzare anche in situazioni critiche! Controllato da pc ovviamente, grazie mille ancora :)

Go Up