Added other tests

Added tests for:
-Average (all cases)
-STD (all cases)
-Anomaly detection (on a uniform distribution)
This commit is contained in:
Vincenzo Pio Florio 2024-11-21 16:35:08 +01:00
parent 4a97a81d7a
commit d31bedd63e
3 changed files with 155 additions and 11 deletions

View File

@ -6,7 +6,7 @@
#include <stdlib.h> #include <stdlib.h>
void initializeReadings(); void initializeReadings();
void freeReadings(); bool freeReadings();
int getSensorsNumber(); int getSensorsNumber();
int getSlidingWindowSize(); int getSlidingWindowSize();
@ -20,6 +20,12 @@ float getOverallAverage();
float getStandardDeviationOnSensor(int sensorIndex); float getStandardDeviationOnSensor(int sensorIndex);
float getStandardDeviationOnAllSensors(); float getStandardDeviationOnAllSensors();
float getStandardDeviationOnAllSensors(); float getOverallStandardDeviation();
float getLastReading(int sensorIndex);
bool anomalyDetect(float average, float standardDeviation);
int getOutlierCount();
#endif // DATA_ACQUISITION_H #endif // DATA_ACQUISITION_H

View File

@ -3,6 +3,8 @@
#include <stdbool.h> #include <stdbool.h>
#include <math.h> #include <math.h>
int outlierCount;
// Variable definition // Variable definition
static float **readings; static float **readings;
static int sensorsNumber; static int sensorsNumber;
@ -35,11 +37,19 @@ void initializeReadings(int numSensors, int windowSize) {
setSlidingWindowSize(windowSize); setSlidingWindowSize(windowSize);
} }
void freeReadings() { bool freeReadings() {
for (int i = 0; i < sensorsNumber; i++) { for (int i = 0; i < sensorsNumber; i++) {
free(readings[i]); free(readings[i]);
} }
if(readings != NULL){
free(readings); free(readings);
return true;
}
else{
return false;
}
} }
// Functions // Functions
@ -64,6 +74,14 @@ bool isFull(int sensorIndex) {
return true; return true;
} }
float getLastReading(int sensorIndex) {
if (isFull(sensorIndex)) {
return readings[sensorIndex][slidingWindowSize - 1];
} else {
return readings[sensorIndex][0];
}
}
// Add a reading to the readings array // Add a reading to the readings array
void addReading(float value, int sensorIndex) { void addReading(float value, int sensorIndex) {
if (isFull(sensorIndex)) { if (isFull(sensorIndex)) {
@ -75,6 +93,8 @@ void addReading(float value, int sensorIndex) {
for (int i = 0; i < slidingWindowSize; i++) { for (int i = 0; i < slidingWindowSize; i++) {
if (readings[sensorIndex][i] == 0) { if (readings[sensorIndex][i] == 0) {
readings[sensorIndex][i] = value; readings[sensorIndex][i] = value;
// Update the position index
break; break;
} }
@ -99,7 +119,7 @@ float getAverageOnSensor(int sensorIndex) {
float getAverageOnAllSensors() { float getAverageOnAllSensors() {
float sum = 0; float sum = 0;
for (int i = 0; i < sensorsNumber; i++) { for (int i = 0; i < sensorsNumber; i++) {
sum += getAverageOnSensor(i); sum += getLastReading(i);
} }
return sum / sensorsNumber; return sum / sensorsNumber;
} }
@ -137,15 +157,33 @@ float getStandardDeviationOnSensor(int sensorIndex) {
float getStandardDeviationOnAllSensors() { float getStandardDeviationOnAllSensors() {
float sum = 0; float sum = 0;
float average = getAverageOnAllSensors();
for (int i = 0; i < sensorsNumber; i++) { for (int i = 0; i < sensorsNumber; i++) {
sum += getStandardDeviationOnSensor(i); float lastReading = getLastReading(i);
sum += pow(lastReading - average, 2);
} }
return sum / sensorsNumber;
return sqrt(sum / sensorsNumber);
}
void anomalyDetect(float average, float standardDeviation) {
float upperThreshold = average + 2.17 * standardDeviation; // 97% confidence interval
float lowerThreshold = average - 2.17 * standardDeviation; // Lower bound for anomaly detection
outlierCount = 0;
for (int i = 0; i < sensorsNumber; i++) {
for (int j = 0; j < slidingWindowSize; j++) {
if (readings[i][j] > upperThreshold || readings[i][j] < lowerThreshold) {
outlierCount++;
}
}
}
} }
float getOverallStandardDeviation() { float getOverallStandardDeviation() {
float sum = 0; float sum = 0;
int totalReadings = 0; int totalReadings = 0;
float totalAverage = getOverallAverage();
for (int i = 0; i < sensorsNumber; i++) { for (int i = 0; i < sensorsNumber; i++) {
if (!isFull(i)) { if (!isFull(i)) {
printf("The sliding window for sensor %d is not full\n", i); printf("The sliding window for sensor %d is not full\n", i);
@ -156,5 +194,14 @@ float getOverallStandardDeviation() {
totalReadings++; totalReadings++;
} }
} }
return sqrt(sum / totalReadings);
float totalStandardDeviation = sqrt(sum / totalReadings);
anomalyDetect(totalAverage, totalStandardDeviation);
return totalStandardDeviation;
}
int getOutlierCount() {
return outlierCount;
} }

View File

@ -3,14 +3,105 @@
#include <math.h> #include <math.h>
#include "../include/dataAcquisition.h" #include "../include/dataAcquisition.h"
#define NUMBER_OF_SENSORS 5
#define SLIDING_WINDOW_SIZE 10
#define AVERAGE_UNCERTAINTY 0.01
#define STD_UNCERTAINTY 0.01
// Testing the inizialization and the instanciacion of the sensors' number and sliding window size
void test_initializeReadings() { void test_initializeReadings() {
initializeReadings(5, 100); initializeReadings(NUMBER_OF_SENSORS, SLIDING_WINDOW_SIZE);
assert(getSensorsNumber() == 5); assert(getSensorsNumber() == NUMBER_OF_SENSORS);
assert(getSlidingWindowSize() == 100); assert(getSlidingWindowSize() == SLIDING_WINDOW_SIZE);
} }
// Testing the logic of add readings to see if the slidinw window is full
void test_addReading() {
for (int sensor = 0; sensor < NUMBER_OF_SENSORS; sensor++) {
for (int value = 1; value <= SLIDING_WINDOW_SIZE; value++) {
addReading(value, sensor);
}
}
assert(isFull(NUMBER_OF_SENSORS-1) == true); // Assuming the last sensor acquired the data
}
// Testing the logic of average methods
void test_averageOnSensor() {
printf("Average on sensor %d: %f\n", NUMBER_OF_SENSORS-1, getAverageOnSensor(NUMBER_OF_SENSORS-1));
float average = getAverageOnSensor(NUMBER_OF_SENSORS-1);
float expected_average = (SLIDING_WINDOW_SIZE + 1) / 2.0;
assert(fabs(average - expected_average) < AVERAGE_UNCERTAINTY);
}
void test_standardDeviationOnSensor() {
printf("Standard deviation on sensor %d: %f\n", NUMBER_OF_SENSORS-1, getStandardDeviationOnSensor(NUMBER_OF_SENSORS-1));
float standard_deviation = getStandardDeviationOnSensor(NUMBER_OF_SENSORS-1);
float expected_standard_deviation = 2.872281323269;
assert(fabs(standard_deviation - expected_standard_deviation) < STD_UNCERTAINTY);
}
void test_averageOnAllSensors() {
printf("Average on all sensors: %f\n", getAverageOnAllSensors());
float average = getAverageOnAllSensors();
float expected_average = SLIDING_WINDOW_SIZE;
assert(fabs(average - expected_average) < AVERAGE_UNCERTAINTY);
}
void test_standardDeviationOnAllSensors() {
printf("Standard deviation on all sensors: %f\n", getStandardDeviationOnAllSensors());
float standard_deviation = getStandardDeviationOnAllSensors();
float expected_standard_deviation = 0;
assert(fabs(standard_deviation - expected_standard_deviation) < STD_UNCERTAINTY);
}
void test_overallAverage(){
printf("Overall average on all sensors: %f\n", getOverallAverage());
float average = getOverallAverage();
float expected_overall_average = (SLIDING_WINDOW_SIZE + 1) / 2.0;
assert(fabs(average - expected_overall_average) < AVERAGE_UNCERTAINTY);
}
void test_overallStandardDeviation(){
printf("Overall standard deviation: %f\n", getOverallStandardDeviation());
float standard_deviation = getStandardDeviationOnSensor(NUMBER_OF_SENSORS-1);
float expected_standard_deviation = 2.872281323269;
assert(fabs(standard_deviation - expected_standard_deviation) < STD_UNCERTAINTY);
}
void test_anomalyDetect(){
float average = getOverallAverage();
float standard_deviation = getOverallStandardDeviation();
anomalyDetect(average, standard_deviation);
printf("Outlier count: %i\n", getOutlierCount());
assert(fabs(getOutlierCount() - 0) < 0.01);
// Adding an outlier
addReading(20, NUMBER_OF_SENSORS-1);
average = getOverallAverage();
standard_deviation = getOverallStandardDeviation();
anomalyDetect(average, standard_deviation);
printf("Outlier count: %i\n", getOutlierCount());
assert(fabs(getOutlierCount() - 1) < 0.01);
}
// TODO: Test all the functions with a normal distribution
// TODO: Evaluate the normal distribution with the anomaly detection
void test_freeReadings() {
assert(freeReadings() == true);
}
int main() { int main() {
test_initializeReadings(); test_initializeReadings();
test_addReading();
test_averageOnSensor();
test_standardDeviationOnSensor();
test_averageOnAllSensors();
test_standardDeviationOnAllSensors();
test_overallAverage();
test_overallStandardDeviation();
test_anomalyDetect();
test_freeReadings();
return 0; return 0;
} }