I am having trouble writing code for moving averages, I wanted to output moving averages from three analog pins. I have attached my entire code, could someone give me some pointers?
Thank you
datalogger_Final_averages.ino (5.3 KB)
I am having trouble writing code for moving averages, I wanted to output moving averages from three analog pins. I have attached my entire code, could someone give me some pointers?
Thank you
datalogger_Final_averages.ino (5.3 KB)
I am having trouble writing code
But, you succeeded in coming up with some code that does something that you did not explain. You want it to do something that you did not explain. For all we know, those two things are the same thing.
gvarghese:
I am having trouble writing code for moving averages, I wanted to output moving averages from three analog pins. I have attached my entire code, could someone give me some pointers?Thank you
typically done with a Circular (Ring) buffer... search the forum you will find examples... here is one for free:
template <class T> class RingBuffer{
public:
RingBuffer(const size_t &size);
void addValue(const T &value);
T getAverage(void) const;
T getMax(void) const;
private:
T* myArray;
size_t arraySize;
uint32_t index;
size_t numElements;
};
template <class T> RingBuffer <T>::RingBuffer(const size_t &size)
{
arraySize = size;
myArray = new T[size];
}
template <class T> void RingBuffer <T>::addValue(const T &value)
{
if(++numElements > arraySize) numElements = arraySize;
myArray[index++] = value;
index %= arraySize;
}
template <class T> T RingBuffer <T>::getAverage(void) const
{
T sum = 0;
for(int i = 0; i < numElements; i++)
{
sum += myArray[i];
}
return (sum / numElements);
}
template <class T> T RingBuffer <T>::getMax(void) const
{
T sum = 0;
for(int i = 0; i < numElements; i++)
{
sum += myArray[i];
}
return (sum / numElements);
}
RingBuffer <float> ringBuffer(10);
void setup(void)
{
Serial.begin(9600);
}
void loop(void)
{
if(Serial.available())
{
float newValue = Serial.parseFloat();
ringBuffer.addValue(newValue);
Serial.print("Added:\t");
Serial.print(newValue, 3);
Serial.print(" to array\tnew average:\t");
Serial.println(ringBuffer.getAverage(), 3);
}
}
Hello,
Thank you for responding back, right now the code takes 40 readings and averages it and saved that value onto a sd card, but I want to do a moving average, I have tried different methods of doing this but have no success, I just wanted some pointers, on how i can do this. I am looking into the circular ring buffer.
Thank you.
I just wanted some pointers
char *pText = "This is a pointer";
char *pCopy = strdup("So is this");
Crude but effective. Each time rawRangeToRam
is updated, the new value is inserted into the buffer and a new average is calculated.
rawRangeToRam_mm = vl.readRange();
status = vl.readRangeStatus();
if (status != VL6180X_ERROR_NONE) displayLaserError(status);
/*
Store the last five range readings in a circular buffer
*/
last5RangeRdg_mm[averagingIndex++] = rawRangeToRam_mm;
if (averagingIndex > avgMax_s - 1) {
averagingIndex = 0; // start over at the first location
}
/*
Sum up the recorded values
*/
avgRange_tmp = 0; // reset average total;
for (byte i = 0; i < avgMax_s; i++) { // i was originally an int
avgRange_tmp += last5RangeRdg_mm[i];
}
/*
Calculate the average of the last five range
readings and copy to working variable
*/
rangeToRam_mm = avgRange_tmp / avgMax_s;