lettura ogni tot e media finale

ciao, sto cercando di rilevare il valore da A0 ogni secondo (che poi nella realtà diventerà 1 minuto), e poi ogni dieci valori fare una media tra loro.
quindi come risultato finale io avrò un valore di media ogni 10 secondi (poi nella realtà 10 minuti)

ma non funziona, ora sul seriale mi spara numeri a raffica e non ogni secondo.
dove sbaglio?
grazie

#include <SoftwareSerial.h>
#define RISCRX 6 //pin ricevitore seriale 
#define RISCTX 7 //pin trasmettitore seriale
int valori[10];
int vdiviso = 0;
unsigned long intervallo = 1000;
unsigned long ritardo = 0;
unsigned long currentMillis = 0;


SoftwareSerial Serialint(RISCRX, RISCTX); //seriale secondaria

void setup() {

  pinMode(RISCTX, OUTPUT);
  pinMode(RISCRX, INPUT);

  Serial.begin(9600);
  Serialint.begin (9600);

}

void loop() {

  for (int i = 0; i < 10; i++) {
    currentMillis = millis();
    if (currentMillis > ritardo) {
      valori[i] = analogRead(A0);
      Serial.print("valore =");
      Serial.println(valori[i]);
      ritardo = currentMillis + intervallo;
    }
  }

  float media = 0.0;
  for (int i = 0; i < 10; i++) {
    media += valori[i];
  }

  media = media / 10.0;
  Serial.println (media);
  vdiviso = (media / 4);
  Serialint.write(vdiviso);
}

Secondo me hai sbagliato come usi la millis()
currmillis ritardo stampo
1000 0 si
1010 2000 si
1020 3000 si

Ragiona su cosa succede qui :

  for (int i = 0; i < 10; i++) {
    currentMillis = millis();
    if (currentMillis > ritardo) {
      valori[i] = analogRead(A0);
      Serial.print("valore =");
      Serial.println(valori[i]);
      ritardo = currentMillis + intervallo;
    }
  }

Prova a scrivere su un foglio i valori che assumono le variabili per ogni step del ciclo (Hint: millis() si incrementerà di pochissimo...)

Ciao, Ale.

Eh, ho provato a scrivere ma mi sembra corretto

>acuplush: Quando si quota un post, NON è necessario riportarlo (inutilmente) tutto; bastano poche righe per far capire di cosa si parla ed a cosa ci si riferisce, inoltre, se si risponde al post immediatamente precedente, normalmente NON è necessario alcun "quote" dato che è sottinteso. :slight_smile:

Gli utenti da device "mobile" (piccoli schermi) ringrazieranno per la cortesia :wink:

Guglielmo

P.S.: Ho eliminato io il "quote" dal tuo post qui sopra :wink:

Facciamo così: spiega nel tuo intento cosa (e come) dovrebbe fare quel codice, perchè quello che fa in realtà non credo sia quello che vuoi.

Ciao, Ale.

Io farei una cosa del genere (pseudo codice; manca anche la punteggiatura: è l'esercizio per te :slight_smile: ):

setup:

i=1
unsigned long t=millis()


loop:

se millis()-t >= 10 minuti
 {
 t=millis()
 leggi A0; valori[i]=leggi A0    (prende la seconda lettura)
 i++
 se i>10 
   {
    somma=0
    for(i=1; i<11; i++) {int somma+=valori[i]}
    scrivi somma/10.0; i=1
   }
 }

Ok Guglielmo, è un vizio che mi è venuto con i gruppi di whatsapp

Il mio intento è quello di ricavare ogni 10 minuti la media di 10 valori (uno ogni minuto), ed inviarla via seriale.
Quindi un invio ogni 10 minuti.

In fondo vedete il valore diviso per 4 perché non sono riuscito a capire come inviare numeri più grandi di 255,quindi ho optato per dividerlo per 4 e nella scheda ricevente lo moltiplico per 4

Devi inviare un lo-byte e un hi-byte: l'hi-byte è il valore diviso 256 (che puoi ottenere con uno shift a destra di 8 bit: valore>>8 ) e il lo-byte è il resto della divisione (valore%256).

Se vuoi farlo in maniera più intuitiva, lo dividi per 100 e quelle sono le centinaia, che poi dovrai moltiplicare per 100; valore%100 sono (le decine e) le unità, che poi dovrai sommare così come sono.

@acuplus, la soluzione è quella di @datman al post#6

Di base questo tuo non ha senso:

for (int i = 0; i < 10; i++) {
   currentMillis = millis();
   if (currentMillis > ritardo) {

La logica NON può essere faccio 10 volte per forza le cose e poi verifico millis()
Prendi esempio BlinkWithoutDelay, lui ogni secondo accende e ogni secondo spegne.
Tu ogni 10 sec fai qualcosa else fa niente.
Cosa fai ogni 10 sec ? Leggi analogico, lo memorizzi. Poi se hai 10 valori letti, allora calcoli media, invii e riazzeri contatore numero letture fatte

rieccomi qui a studiare... grazie per i consigli!
ho riscritto completamente il codice e sembra funzionare abbastanza bene (per ora non ho ancora preso in mano il discorso lo-byte /hi-byte, faccio un passo alla volta)
ho aggiunto un po di serialprint per capire come lavora e ho trovato un'anomalia, praticamente mi fà 10 letture (giustamente ogni 2 secondi come ho impostato) , poi ne fà un'altra completamente sballata (e sempre diversa) per poi passare alla somma, media, divisione.
come mai? forse perchè è una "casella" non assegnata?

edit: penso di aver capito...devo mettere if i>9 dato che le caselle partono dalla 0. infatti così sembra lavorare bene.
ottimo lavoro ragazzi grazie!!
ora studio un po il discorso dei byte

qui il serialprint:

valore =730
valore =729
valore =729
valore =729
valore =729
valore =729
valore =730
valore =730
valore =729
valore =730
valore =26463
somma =730
somma =1459
somma =2188
somma =2917
somma =3646
somma =4375
somma =5105
somma =5835
somma =6564
somma =7294
media =729
dimezzato =182

qui il codice:

#include <SoftwareSerial.h>
#define RISCRX 6 //pin ricevitore seriale 
#define RISCTX 7 //pin trasmettitore seriale
int valori[10];
int vdiviso = 0;
unsigned long intervallo = 2000;
unsigned long previousMillis = 0;
unsigned long currentMillis = 0;
int somma = 0;
int i = 0;
int media = 0;


SoftwareSerial Serialint(RISCRX, RISCTX); //seriale secondaria

void setup() {

  pinMode(RISCTX, OUTPUT);
  pinMode(RISCRX, INPUT);

  Serial.begin(9600);
  Serialint.begin (9600);

}

void loop() {
  currentMillis = millis();
  if (currentMillis - previousMillis >= intervallo) {
    previousMillis = currentMillis;
    valori[i] = analogRead(A0);
    Serial.print("valore =");
    Serial.println(valori[i]);
    i++;
  }
  if (i > 10) {
    somma = 0;
    i = 0;
    for (int i = 0; i < 10; i++) {
      somma += valori[i];
      Serial.print("somma =");
      Serial.println(somma);
    }
    media = somma / 10;
    Serial.print("media =");
    Serial.println(media);
    vdiviso = (media / 4);
    Serial.print("dimezzato =");
    Serial.println(vdiviso);
    Serialint.write(vdiviso);
    i = 0;
  }
}