Dudas sobre como implementar un cambio en la frecuencia de muestreo

Hola comunidad, estuve leyendo acerca sobre la frecuencia de muestreo, encontré justo lo que necesitaba en un post de Luis Llamas, lo implementé con un sensor de temperatura solo para probarlo, el codigo que diseñé es este:

#include <OneWire.h>                
#include <DallasTemperature.h>
 
OneWire ourWire(2);                //Se establece el pin 2  como bus OneWire
 
DallasTemperature sensors(&ourWire); //Se declara una variable u objeto para nuestro sensor

void setup() {
float measureT = MeasureT(100, temp);  
delay(1000);
Serial.begin(9600);
sensors.begin();   //Se inicia el sensor
}
 
void loop() {
sensors.requestTemperatures();   //Se envía el comando para leer la temperatura
float temp= sensors.getTempCByIndex(0); //Se obtiene la temperatura en ºC

Serial.print("Temperatura= ");
Serial.print(temp);
Serial.println(" C");
delay(100);                     
}

float MeasureT(int msInterval, float(*funct)())
{
   float sum;
   long startTime = millis();
   int samplesNumber = 0;

   while (millis() - startTime < msInterval)
   {
      samplesNumber++;
      sum += temp();
   }
   return sum / samplesNumber;
}

//Funcion que simula la medicion de un sensor
float temp()
{
   return 0.0;
}

creo que no comprendí bien, porque no veo ningún cambio en el monitor serie, entiendo que el valor que debo hacer variar se encuentra en esta línea de código:

float measureT = MeasureT(100, temp);  

cambio de 100 a 200, y 500 y no hay variación en los resultados, ¿estoy interpretando incorrectamente el código?, por ejemplo, si quiero que me tome las mediciones de temperatura cada 1 segundo, haga una media aritmética de los valores recogidos por el sensor dentro de ese segundo y luego los muestre, de eso trata la sección " ADQUISICIÓN EN TIEMPO CONSTANTE" en el post que linkee más arriba (este)?

Saludos!

Ya que no nos dices que valores te devuelve imagino que siempre obtienes 0.0, ¿verdad?

temp() es una función ficticia ("dummy") que solo devuelve 0.0, no hace una medición real.
De hecho lo aclara en el código

//Funcion que simula la medicion de un sensor

La palabra clave es simula. :wink:

Tienes que cambiarla por la verdadera función que efectúa la lectura del sensor.

Saludos

Creo mas bien que devuelve constamtemente el valor de la temperatura que da el sensor.
@and_jc Observa que tu loop no llamas ala funcion de frecuencia de muestreos , solo llamas al sensor con las dos primeras lineas y el te devuelve directamente la temperatura:

sensors.requestTemperatures();   //Se envía el comando para leer la temperatura
float temp= sensors.getTempCByIndex(0); //Se obtiene la temperatura en ºC

estas dos lineas has de incluirlas en la funcion de simulacion que quedaria :

//Funcion que hace una medicion
float temp(){
  sensors.requestTemperatures();   //Se envía el comando para leer la temperatura
  float temp = sensors.getTempCByIndex(0); //Se obtiene la temperatura en ºC
  return temp;
}

y sustituirlas en el loop por la llamada a la rutina de muestreo.
Saludos.

Yo sugiero que en la función simulada ponga un random que devuelva valores entre ciertos limites.

Otra cosilla @and_jc En la funcion:

float MeasureT(int msInterval, float(*funct)())
{
   float sum;
   long startTime = millis();
   int samplesNumber = 0;
   etc....

Tienes tambien que reseterar la variable "sum" o se te van acumulando los valores de anteriores llamadas a la funcion:

float MeasureT(int msInterval, float(*funct)())
{
   float sum = 0 ;
   long startTime = millis();
   int samplesNumber = 0;
   etc....

Saludos.

Ya que no nos dices que valores te devuelve imagino que siempre obtienes 0.0, ¿verdad?

No, el sensor me arrojaba la temperatura real, pero sin cambios luego de introducir el codigo perteneciente a la frecuencia de muestreo.

temp() es una función ficticia ("dummy") que solo devuelve 0.0, no hace una medición real.
De hecho lo aclara en el código

El código original de la pagina web que linkee es este:

float MeasureT(int msInterval, float(*funct)())
{
   float sum;
   long startTime = millis();
   int samplesNumber = 0;

   while (millis() - startTime < msInterval)
   {
      samplesNumber++;
      sum += getMeasure();
   }
   return sum / samplesNumber;
}

//Funcion que simula la medicion de un sensor
float getMeasure()
{
   return 0.0;
}

void setup()
{
   float measureT = MeasureT(50, getMeasure);
}

void loop()
{

}

Si te fijas, cambié "float getMeasure()" por "float temp();", pero aún así no me funciona :confused:

Si, en mi respuesta por mirar el código de Luis Llamas no me había dado cuenta que lo habias cambiado para que leyera el sensor. Mala mía.

La solución es la que te dijo @gonpezzi , o sea, te falta cambiar temp() para que realmente lea el sensor.

Saludos

Muchas gracias por tu orientación, cambié mi codigo según tus consejos, pero ahora no sé porque me sale el error "'temp' was not declared in this scope" y ya está declarado en las líneas precedentes según yo, me quedó asi:

#include <OneWire.h>                
#include <DallasTemperature.h>
 
OneWire ourWire(2);                //Se establece el pin 2  como bus OneWire
 
DallasTemperature sensors(&ourWire); //Se declara una variable u objeto para nuestro sensor

void setup() {
float measureT = MeasureT(100, temp);  
delay(1000);
Serial.begin(9600);
sensors.begin();   //Se inicia el sensor
}
 
void loop() {
//Funcion que simula la medicion de un sensor
float temp()
{  sensors.requestTemperatures();   //Se envía el comando para leer la temperatura
   float temp= sensors.getTempCByIndex(0); //Se obtiene la temperatura en ºC
   return temp;
}

Serial.print("Temperatura= ");
Serial.print(temp);
Serial.println(" C");
delay(100);                     
}

float MeasureT(int msInterval, float(*funct)())
{
   float sum=0;
   long startTime = millis();
   int samplesNumber = 0;

   while (millis() - startTime < msInterval)
   {
      samplesNumber++;
      sum += temp();
   }
   return sum / samplesNumber;
}


En realidad, no me manejo mucho en programación con Arduino, lo que quiero hacer es unir el código de medición de temperatura, este:

#include <OneWire.h>                
#include <DallasTemperature.h>
 
OneWire ourWire(2);                //Se establece el pin 2  como bus OneWire
 
DallasTemperature sensors(&ourWire); //Se declara una variable u objeto para nuestro sensor

void setup() {
float measureT = MeasureT(10,temp);  
delay(1000);
Serial.begin(9600);
sensors.begin();   //Se inicia el sensor
}
 
void loop() {
sensors.requestTemperatures();   //Se envía el comando para leer la temperatura
float temp= sensors.getTempCByIndex(0); //Se obtiene la temperatura en ºC

Serial.print("Temperatura= ");
Serial.print(temp);
Serial.println(" C");
delay(100);                     
}

float MeasureT(int msInterval, float(*funct)())
{
   float sum;
   long startTime = millis();
   int samplesNumber = 0;

   while (millis() - startTime < msInterval)
   {
      samplesNumber++;
      sum += temp();
   }
   return sum / samplesNumber;
}

//Funcion que simula la medicion de un sensor
float temp()
{  sensors.requestTemperatures();   //Se envía el comando para leer la temperatura
   float temp = sensors.getTempCByIndex(0); //Se obtiene la temperatura en ºC
   return temp;
}

con el codigo de Luis Llamas, que es este:

float MeasureT(int msInterval, float(*funct)())
{
   float sum;
   long startTime = millis();
   int samplesNumber = 0;

   while (millis() - startTime < msInterval)
   {
      samplesNumber++;
      sum += getMeasure();
   }
   return sum / samplesNumber;
}

//Funcion que simula la medicion de un sensor
float getMeasure()
{
   return 0.0;
}

void setup()
{
   float measureT = MeasureT(50, getMeasure);
}

void loop()
{

}

Lo que quiero es una medida por seguno o cada dos segundos pero que el codigo haga un promedio de los valores recibidos por el sensor, tal como lo dice Luis Llamas en su blog:

ADQUISICIÓN EN TIEMPO CONSTANTE
Una variación es medir en un intervalo de tiempo constante. Ejemplo, tomamos un sensor y decidimos que queremos realizar todas las mediciones posibles durante 20, o 50 o 100 ms.

Saludos!

Cambia esto

void loop() {
Serial.print("Temperatura= ");
Serial.print(MeasureT(100, temp),1);
Serial.println(" C");
delay(100);                     
}

El error que te dió se debe a que el loop() te quedó corrupto, pegaste la función temp() en medio. :man_facepalming:t2:

Me corrijo hazlo así para que sea más entendible

#include <OneWire.h>                
#include <DallasTemperature.h>
 
OneWire ourWire(2);                //Se establece el pin 2  como bus OneWire
 
DallasTemperature sensors(&ourWire); //Se declara una variable u objeto para nuestro sensor

float medicion;

void setup() {
// medicion = MeasureT(100, temp);  // está mal, todavia sensors no fue iniciado
//delay(1000); // este delay tampoco
Serial.begin(9600);
sensors.begin();   //Se inicia el sensor
}
 
void loop() {
medicion = MeasureT(100, temp);  
Serial.print("Temperatura= ");
Serial.print(medicion,1); // imprime float con 1 decimal
Serial.println(" C");
delay(100);                     
}


float temp()
{  sensors.requestTemperatures();   //Se envía el comando para leer la temperatura
   float temp= sensors.getTempCByIndex(0); //Se obtiene la temperatura en ºC
   return temp;
}

float MeasureT(int msInterval, float(*funct)())
{
   float sum=0;
   long startTime = millis();
   int samplesNumber = 0;

   while (millis() - startTime < msInterval)
   {
      samplesNumber++;
      sum += temp();
   }
   return sum / samplesNumber;
}

Como usar una variable (measureT) con nombre casi igual a una funcion (MeasureT()) genera confusión, cambié measureT por medicion.

Muchas gracias @anon90500195 , me funcionó con el sensor de temperatura, ahora lo implementé en un sensor de presión con un datalogger y tengo algunas dudas con el intervalo de tiempo, puedes verlo acá: Confundido con el intervalo de tiempo en la reducción del ruido en un sensor - Español / Software - Arduino Forum.

Pero muchas gracias por tu inmensa ayuda.