DATALOGGER: Miglior metodo per salvare su SD con successiva realizzazione grafic

Buongiorno a tutti,
So bene come memorizzare su SD dei dati (letture di sensori) ma quello che più mi interessa è poi come visualizzarli su un database in un successivo momento, oppure fare dei confronti con diversi intervalli di tempo. Quindi, avevo pensato di utilizzare i grafici di Excel. Salvando diversi file .csv su SD con nome:

  • Giornaliero
  • Settimanale
  • Mensile
    etc..

Ma poi con il tempo mi sono accorto che non può funzionare questo sistema semplicemente perchè quando arduino gira per anche 2 settimane senza che io svuoti il file giornaliero, quest'ultimo si riempie di migliaia di dati in cui poi la lettura successiva in Excel è praticamente impossibile perchè farà un grafico con centinaia di scritte nel periodo del tempo, esattamente cosi:

Quindi ho un problema su come conservare questi dati...non mi posso mettere ogni giorno a sfilare la SD da arduino, salvare il file su PC rinominando il giorno e poi inserire nuovamente la SD su arduino...purtroppo arduino starà in una zona in cui non è possibile utilizzare internet. Qualcuno ha qualche suggerimento? :confused: :confused:

Non ho capito qual'è il problema. Se i dati sono tanti, il grafico puoi farlo selezionando solo una parte dei dati !! Però questo è una conoscenza di Excel e non Arduino.

Ma il file giornaliero è sempre lo stesso ? Perchè non fare file separati, uno per ogni giorno ?

E l'ideale sarebbe appunto quello.
Ogni giorno, si crea un file diverso rinominato con giorno e mese attuale per esempio file giornalieri rinominati tipo:

22_Mar
23_Mar
24_Mar
Etc..

Poi, per esempio fare dei file settimanali rinominati:

27feb_05mar
6mar_12mar
13mar_19mar
20mar_26mar
27mar_02apr

In cui solo e soltanto dati provenienti in quei giorni devono essere memorizzati in quei file.
Ci avevo pensato pure per questa cosa, ma potrei riuscirci rinominando personalmente tutti i file scrivendo sullo sketch per esempio:

HCRTC.RTCRead(I2CDS1307Add);
  if (semaforo == 0 && HCRTC.GetTimeString() == 22/03/17)
  { DataFile = SD.open("22_mar.csv", FILE_WRITE);
    if (DataFile)
    { semaforo = 1;
      { ScriviFileConData(t, h);
      }
    }
  }

HCRTC.RTCRead(I2CDS1307Add);
  if (semaforo == 0 && HCRTC.GetTimeString() == 23/03/17)
 { 
DataFile = SD.open("23_mar.csv", FILE_WRITE);
    if (DataFile)
    { semaforo = 1;
      { ScriviFileConData(t, h);
      }
    }
  }

(Sketch per soli due giorni, 22 e 23 marzo)
Ma cosi sono io che scrivo i file, non è arduino che capisce in base alla data quale file creare e con quale rinominatura.. questo significa che dovrei riempire uno sketch di tantissime righe per ogni giorno dell'anno...spero ci sia un altro metodo a questo.
Meglio poi gestire questo problema con Arduino piuttosto che Excel..se no poi con quest'ultimo dovrei selezionare manualmente i dati.

A proposito...sapevo poi che il nome di un file su SD non può superare gli 8 caratteri..è vero?

Devi creare il nome del file che dipende dalla data.

char nomefile[13];
...
sprintf(nomefile,"%04d%02d%02d.cvs",HCRTC.GetYear(),HCRTC.GetMonth(),HCRTC.GetDay());
se la data è 1/2/2017 otterrai 20170201.csv (AAAAMMGG)

oppure
sprintf(nomefile,"%02d_%02d_%02d.cvs",HCRTC.GetYear()%100,HCRTC.GetMonth(),HCRTC.GetDay());
se la data è 1/2/2017 otterrai 17_02_01.csv (AA_MM_GG)

ciao nid, scusami se ti sto rispondendo adesso..ho avuto modo di leggere ora il tuo prezioso contributo e quindi ho fatto questo sketch:

void ScriviFileGiornoData(float t, float h)
{ HCRTC.RTCRead(I2CDS1307Add);
  if (HCRTC.GetHour() == 0 && HCRTC.GetMinute() == 0)
  { if (semaforo == 0)
      DataFile = SD.open(sprintf(nomefile,"%02d_%02d_%02d.cvs",HCRTC.GetYear()%100,HCRTC.GetMonth(),HCRTC.GetDay()), FILE_WRITE);
    if (DataFile)
    {
      semaforo = 1;
      Serial.println("OK mem. mezzanotte");
      DataFile.print(HCRTC.GetDateString());
      DataFile.print(";");
      if (HCRTC.GetHour() < 10) DataFile.print("0");
      DataFile.print(HCRTC.GetHour());
      DataFile.print(":");
      if (HCRTC.GetMinute() < 10) DataFile.print("0");
      DataFile.print(HCRTC.GetMinute());
      DataFile.print(";");
      DataFile.print(t);
      DataFile.print(";");
      DataFile.print(h);
      DataFile.println(";");
      DataFile.close();
    }
  }
  else
  { semaforo = 0;
  }
}

dove:

char nomefile[13];

l'ho dichiarato come variabile globale...purtroppo però non mi stampa in seriale, e difatti non memorizza su SD..ho interpretato male la tua stringa?

Grazie ancora..

devi farlo in due passaggi, la sprintf() modifica il primo parametro mentre ritorna semplicemente il numero di caratteri scritti (cosa che ci interessa poco).

char nomefile[15];
sprintf(nomefile,"%02d_%02d_%02d.cvs",HCRTC.GetYear()%100,HCRTC.GetMonth(),HCRTC.GetDay())
DataFile = SD.open(nomefile, FILE_WRITE);

Buon pomeriggio. Mi inserisco in questo post. Io utilizzo la libreria DS3231 per leggere data e ora.

Non riesco a compilare in quanto ho il classico messaggio:

HCRTC was not declared in this scope

tutto questo in corrispondenza della riga di sprintf().

C è qualche cosa da modificare?

Posta il tuo codice. Dovrebbe mancare la dichiarazione dell'oggetto RTC. Ma senza vedere quel che hai scritto...

Si scusami ecco a te il codice di esempio:

#include <SD.h>   //SD
#include <SPI.h> //SD
#include <DS3231.h> //OROLOGIO
#include <Wire.h> //OROLOGIO


File myFile;
int pinCS = 53; //  SD Pin 10 on Arduino Uno
DS3231  rtc(SDA, SCL);

char nomefile[13];

void setup() {
 Serial.begin(9600);
rtc.begin();
pinMode(pinCS, OUTPUT); //SD

  
  
  // SD Card Initialization
  if (SD.begin())
  {
    Serial.println("SD card is ready to use.");
  } else
  {
    Serial.println("SD card initialization failed");
    return;
  }
 
}

void loop() {
  sprintf(nomefile,"%04d%02d%02d.txt", HCRTC.GetYear(),HCRTC.GetMonth(),HCRTC.GetDay());
  myFile=SD.open(nomefile,FILE_WRITE);
 
 if(myFile){
 myFile.print("TEST DATA");
 myFile.close();
 }
 else{
  Serial.println("error opening");
  }
  delay(3000);
 }

nel codice di Gianky lui usa un oggetto rtc di nome HCRTC
tu invece devi usare la parola rtc
quindi dove vedi HCRTC devi sostituire con rtc

ciao, ho fatto la sostituzione come mi hai indicato.

#include <SD.h>   //SD
#include <SPI.h> //SD
#include <DS3231.h> //OROLOGIO
#include <Wire.h> //OROLOGIO


File myFile;
int pinCS = 53; //  SD Pin 10 on Arduino Uno
DS3231  rtc(SDA, SCL);

char nomefile[15];

void setup() {
 Serial.begin(9600);
rtc.begin();
pinMode(pinCS, OUTPUT); //SD

  
  
  // SD Card Initialization
  if (SD.begin())
  {
    Serial.println("SD card is ready to use.");
  } else
  {
    Serial.println("SD card initialization failed");
    return;
  }
 
}

void loop() {
  sprintf(nomefile,"%04d%02d%02d.txt", rtc.GetYear(),rtc.GetMonth(),rtc.GetDay());
  myFile=SD.open(nomefile,FILE_WRITE);
 
 if(myFile){
 myFile.print("TEST DATA");
 myFile.close();
 }
 else{
  Serial.println("error opening");
  }
  delay(3000);
 }

purtroppo mi da il seguente errore:

"class D3231 has no member named 'GetYear' "

Ho come l'impressione che si debba cercare la funzione apposita per tirare fuori l'anno, il mese ed il giorno.

Giusto?

Guarda della libreria che usi il file .h
Dentro ci deve essere una qualche funzione (metodo) della classe per ottenere l'anno. In C le maiuscole/minuscole fanno differenza. Forse la tua lib non usa GetYear() ma getYear() oppure getyear()
Stessa cosa per giorno e mese

Nid, volevo ringraziarti comunque per la risposta datami...non ho modo per adesso di provarlo perchè non ho sottomano un modulo SD ma ti ringrazio comunque, non appena l'avrò proverò il tuo codice :smiley:

nid69ita:
Guarda della libreria che usi il file .h
Dentro ci deve essere una qualche funzione (metodo) della classe per ottenere l'anno. In C le maiuscole/minuscole fanno differenza. Forse la tua lib non usa GetYear() ma getYear() oppure getyear()
Stessa cosa per giorno e mese

Grazie. Spulciando nella libreria sono riuscito a risolvere.