LUIS

Dependencies:   mbed

Files at this revision

API Documentation at this revision

Comitter:
pirottealex
Date:
Fri Oct 05 14:54:02 2018 +0000
Commit message:
a

Changed in this revision

digital_filter.cpp Show annotated file Show diff for this revision Revisions of this file
digital_filter.h Show annotated file Show diff for this revision Revisions of this file
main.cpp Show annotated file Show diff for this revision Revisions of this file
mbed.bld Show annotated file Show diff for this revision Revisions of this file
diff -r 000000000000 -r 7a912bfb5a4e digital_filter.cpp
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/digital_filter.cpp	Fri Oct 05 14:54:02 2018 +0000
@@ -0,0 +1,122 @@
+/**
+ *  digital_filter.h
+ *
+ *  Auteur : Ferdinand Piette (Avril 2011)
+ *  Version : 1.0b
+ *
+ *  Fourni des fonctions permettant d'appliquer des filtres numériques
+ *  ayant pour fonction de transfert :
+ *
+ *          b0*z + b1*z^-1 + ... + bN*z^-N
+ *  H(z) = --------------------------------
+ *           1 + a1*z^-1 + ... + aM*z^-M
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+
+#include "digital_filter.h"
+
+/**
+ * Initialise les coefficiants du filtre
+ * @param coef_a : les coefficients ai de la fonction de transfert du filtre
+ * @param coef_b : les coefficients bj de la fonction de transfert du filtre
+ * @param coef_a_size : le nombre de coefficients ai. Correspond à M dans la fonction de transfert du filtre
+ * @param coef_b_size : le nombre de coefficients bi. Correspond à N dans la fonction de transfert du filtre
+ * @param transfert_function : un pointeur vers la structure digital_filter_coefficient à initialiser
+ * Si coef_a_size = 0, alors on a la fonction de transfert d'un filtre RIF, sinon, on a celle d'un filtre RII
+ */
+void init_digital_filter_coefficient(struct digital_filter_coefficient * transfert_function, double * coef_a, int coef_a_size, double * coef_b, int coef_b_size)
+{
+    int i;
+
+    // Création du tableau des coefficients a
+    transfert_function->numberOfCoef_a = coef_a_size;
+    transfert_function->coef_a = (double *)malloc(transfert_function->numberOfCoef_a * sizeof * transfert_function->coef_a);
+    for(i = 0; i < transfert_function->numberOfCoef_a; i++)
+        transfert_function->coef_a[i] = coef_a[i];
+
+    // Création du tableau des coefficients b
+    transfert_function->numberOfCoef_b = coef_b_size;
+    transfert_function->coef_b = (double *)malloc(transfert_function->numberOfCoef_b * sizeof * transfert_function->coef_b);
+    for(i = 0; i < transfert_function->numberOfCoef_b; i++)
+        transfert_function->coef_b[i] = coef_b[i];
+}
+
+/**
+ * Initialise le filtre
+ * @param coef_a : les coefficients ai de la fonction de transfert du filtre
+ * @param coef_b : les coefficients bj de la fonction de transfert du filtre
+ * @param coef_a_size : le nombre de coefficients ai. Correspond à M dans la fonction de transfert du filtre
+ * @param coef_b_size : le nombre de coefficients bi. Correspond à N dans la fonction de transfert du filtre
+ * @param filter : un pointeur vers la structure digital_filter à initialiser
+ * Si coef_a_size = 0, alors on se ramène à un filtre RIF, sinon, on a un filtre RII
+ */
+void init_digital_filter(struct digital_filter * filter, double * coef_a, int coef_a_size, double * coef_b, int coef_b_size)
+{
+    // Initialise les coefficients du filtre
+    init_digital_filter_coefficient(&filter->transfert_function, coef_a, coef_a_size, coef_b, coef_b_size);
+
+    // Alloue l'espace mémoire pour les échantillons et les résultats
+    filter->samples = (double *)calloc(filter->transfert_function.numberOfCoef_b, sizeof * filter->samples);
+    filter->results = (double *)calloc(filter->transfert_function.numberOfCoef_a, sizeof * filter->results);
+
+    // Initialise les pointeurs des tableaux d'échantillons et de résultats
+    filter->current_sample = 0;
+    filter->previous_result = filter->transfert_function.numberOfCoef_a-1;
+}
+
+/**
+ * Calcul l'échantillon après filtrage
+ * @param sample : le nouvel échantillon que l'on veut filtrer
+ * @param filter : un pointeur vers la structure digital_filter contenant les informations du filtre (fonction de transfert et mémoire des échantillons précédents)
+ * @return l'échantillon après filtrage
+ */
+double filter_next_sample(digital_filter * filter, double sample)
+{
+    double result = 0;
+    int i;
+
+    // Stocke en mémoire le nouvel échantillon
+    filter->samples[filter->current_sample] = sample;
+
+    // Calcul le résultat du filtrage pour un filtre RIF ou RII
+    // (Prise en compte des échantillons précédent)
+    for(i = 0; i < filter->transfert_function.numberOfCoef_b; i++)
+        result += filter->transfert_function.coef_b[i] * filter->samples[modulo((filter->current_sample-i),filter->transfert_function.numberOfCoef_b)];
+
+    // Calcul le résultat du filtrage pour un filtre RII
+    // (Correction avec le résultat du filtrage des échantillons précédents)
+    for(i = 0; i < filter->transfert_function.numberOfCoef_a; i++)
+        result -= filter->transfert_function.coef_a[i] * filter->results[modulo((filter->previous_result-i),filter->transfert_function.numberOfCoef_a)];
+
+    // Met à jours les pointeurs des tableaux d'échantillons et de résultats
+    filter->current_sample = (filter->current_sample + 1) % filter->transfert_function.numberOfCoef_b;
+    if(filter->transfert_function.numberOfCoef_a > 0)
+    {
+        filter->previous_result = (filter->previous_result + 1) % filter->transfert_function.numberOfCoef_a;
+        filter->results[filter->previous_result] = result;  // Garde en mémoire le résultat pour l'échantillon en cours
+    }
+
+    return result;
+}
+
+/**
+ * Définie l'opération de modulo dans les négatifs pour manipuler des buffers circulaires
+ * @param number : le nombre modulé
+ * @param n : le nombre modulant
+ * @return number modulo n
+ * modulo(-1, 3) = 2
+ */
+int modulo(int number, int n)
+{
+    if(number >= 0)
+        return number%n;
+
+    int result = (-1*number)%n;
+
+    if(result > 0)
+        return n-result;
+
+    return 0;
+}
diff -r 000000000000 -r 7a912bfb5a4e digital_filter.h
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/digital_filter.h	Fri Oct 05 14:54:02 2018 +0000
@@ -0,0 +1,47 @@
+/**
+ *  digital_filter.h
+ *
+ *  Auteur : Ferdinand Piette (Avril 2011)
+ *  Version : 1.0b
+ *
+ *  Fourni des fonctions permettant d'appliquer des filtres numériques
+ *  ayant pour fonction de transfert :
+ *
+ *          b0*z + b1*z^-1 + ... + bN*z^-N
+ *  H(z) = --------------------------------
+ *           1 + a1*z^-1 + ... + aM*z^-M
+ */
+
+#ifndef DEF_digital_filter
+#define DEF_digital_filter
+
+    /**
+     * Structure stockant les coefficients du filtre
+     */
+    typedef struct digital_filter_coefficient
+    {
+        double * coef_a;        // Les coefficients a1..aN
+        double * coef_b;        // Les coefficients b0..bM
+        int numberOfCoef_a;     // Le nombre de coefficients a
+        int numberOfCoef_b;     // Le nombre de coefficients b
+    } digital_filter_coefficient;
+
+    /**
+     * Structure stockant les coefficiants du filtre et les échantillons et résultats nécessaires
+     */
+    typedef struct digital_filter
+    {
+        double * samples;       // Les échantillons en entrées du filtre
+        double * results;       // Le résultat de la sortie du filtre
+        int current_sample;     // L'indice du tableau où se trouvera le prochain échantillon
+        int previous_result;    // L'indice du tableau où se trouve la sortie du filtre pour l'échantillon courrant
+        struct digital_filter_coefficient transfert_function;   // La structure stockant les coefficients du filtre
+    } digital_filter;
+
+    void init_digital_filter_coefficient(struct digital_filter_coefficient *, double *, int, double * , int);   // Initialise les coefficients du filtre
+    void init_digital_filter(struct digital_filter *, double *, int, double * , int);                           // Initialise le filtre
+    double filter_next_sample(digital_filter *, double);        // Calcule la sortie du filtre pour un nouvel échantillon
+
+    int modulo(int, int);   // Fonction modulo pour buffer circulaire (modulo(-1, 3) = 2)
+
+#endif
diff -r 000000000000 -r 7a912bfb5a4e main.cpp
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/main.cpp	Fri Oct 05 14:54:02 2018 +0000
@@ -0,0 +1,28 @@
+#include "mbed.h"
+#include "digital_filter.h"
+
+
+Serial pc(USBTX,USBRX);
+
+int main()
+{
+    pc.baud(460800);
+
+    double coef_b[4] = {0.0408, 0.1224, 0.1224, 0.0408};    // Les 4 coefficients ai
+    double coef_a[3] = {-1.2978, 0.7875, -0.1632};          // Les 3 coefficients bj
+    double echantillons[32] = {0.7362, 0.2071, 1.2774, 1.0, 0.5703, 1.2071, 0.0291, 0.0, -0.0291, -1.2071, -0.5703, -1.0, -1.2774, -0.2071, -0.7362, 0.0,
+                               0.7362, 0.2071, 1.2774, 1.0, 0.5703, 1.2071, 0.0291, 0.0, -0.0291, -1.2071, -0.5703, -1.0, -1.2774, -0.2071, -0.7362, 0.0};
+    digital_filter mon_filtre;
+
+    init_digital_filter(&mon_filtre, coef_a, 4, coef_b, 3); // Initialisation du filtre avec les coefficients de la fonction de transfert
+
+    for(char i = 0; i < 32; i++)
+    { // On filtre les échantillons
+        pc.printf("Echantillon numero %d : %lf\t | Apres filtrage : %lf\n\r", i, echantillons[i], filter_next_sample(&mon_filtre, echantillons[i]));
+    }
+
+    while(1)
+    {
+        wait(1);
+    }
+}
diff -r 000000000000 -r 7a912bfb5a4e mbed.bld
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mbed.bld	Fri Oct 05 14:54:02 2018 +0000
@@ -0,0 +1,1 @@
+https://os.mbed.com/users/mbed_official/code/mbed/builds/5aab5a7997ee
\ No newline at end of file