Forum: Mikrocontroller und Digitale Elektronik Ausreißer weg filtern


von Markus (Gast)


Lesenswert?

Hallo an alle,

welche Methoden verwendet ihr, um Ausreißer z.B. von einem Sensor weg zu 
filtern?

Mit einem Mittelwert kann man zwar Messwerte glätten, aber ein starker 
Ausreißer verzieht den Wert trotzdem.

Diesen Filter kenne ich nicht ( Methode nach Grubbs ), macht aber einen 
viel versprechenden Eindruck:

http://de.wikihow.com/Ausrei%C3%9Fer-nach-Grubbs-berechnen

von StinkyWinky (Gast)


Lesenswert?

Medianfilter

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Markus schrieb:
> Methode nach Grubbs
Das ist im ersten Schritt ein Medianfilter: sortiere eine (am besten 
ungerade) Zahl von Messwerten und nimm den in der Mitte. Bei einer 
geraden Zahl von Messwerten musst du noch zusätzlich den Mittelwert der 
beiden mittleren bilden...

Und alles, was danach kommt, ist nur noch weitere Statistik zur 
Zuverlässigkeit des Messwerts. Das ist in der alltäglichen Praxis 
unnötig.

: Bearbeitet durch Moderator
von Ingo L. (corrtexx)


Lesenswert?

Markus schrieb:
> welche Methoden verwendet ihr, um Ausreißer z.B. von einem Sensor weg zu
> filtern?
1
int32_t Limit_Spike ( int32_t Value )
2
{
3
  static int32_t LastValue = 0;
4
  int32_t Difference = Value - LastValue;
5
6
  if ( Difference > DIFMAX ) Value += DIFMAX;
7
  if ( Difference < -DIFMAX) Value -= DIFMAX;
8
9
  if ( Value < VALMIN ) Value = VALMIN;
10
  if ( Value > VALMAX ) Value = VALMAX;
11
12
  LastValue = Value;
13
  return Value;
14
}

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Ingo L. schrieb:
> int32_t Limit_Spike ( int32_t Value )
Zu deiser Methode gehört aber auch eine gehörige Portion an 
"Ausprobieren", um die 4 Konstanten zur Limitierung zu finden. 
"Portabel" und "Einfach" schreiben sich anders...

von Ingo L. (corrtexx)


Lesenswert?

Du behauptest grade das man vorher überlegen sollte was man tut. Das 
muss man doch aber immer.

Gerade bei Reglern macht sowas Sinn, damit man immer vorhersagbares 
Verhalten hat

: Bearbeitet durch User
von chris (Gast)


Lesenswert?

Lothar Miller (lkmiller) (Moderator) Benutzerseite
>Und alles, was danach kommt, ist nur noch weitere Statistik zur
>Zuverlässigkeit des Messwerts. Das ist in der alltäglichen Praxis
>unnötig.

Ich glaube, das ist zu unvollständig. Die Methode nach Grubbs ist näher 
an  der Matlab-Funktion "trimmean", bei der beispielsweise die oberen 
und unteren 10% der sortierten Folge weggelassen werden:

http://de.mathworks.com/help/stats/trimmean.html?requestedDomain=www.mathworks.com

von chris (Gast)


Lesenswert?

Ingo Less (corrtexx)
1
int32_t Limit_Spike ( int32_t Value )

Hall Ingo,

das ist interessant. Ich hatte einen ähnlichen Ansatz. Allerdings passe 
ich die Grenzen mittels eines LowPassFilters statt mit konstanter 
Schrittweite an.

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Ingo L. schrieb:
> Du behauptest grade das man vorher überlegen sollte was man tut.
Das ist eine recht freie Interpretation meiner Aussage. Sie stimmt 
allerdings.

Nur weiß man gerade bei Ausreißern nicht, wie stark sie ausreißen. 
Und deshalb funktioniert ein Medianfilter tendenziell zuverlässiger als 
das Begrenzen von Werten jenseits des gewünschten/erwarteten/geplanten 
Bereichs.

Allerdings wende ich jede Art von Filterung von Messwerten erst an, wenn 
ich sicher weiß(!) whoer die Störungen kommen. Denn sonst ist so ein 
Filter einfach nur ein "Schönsaufen"...

chris schrieb:
> Ich hatte einen ähnlichen Ansatz. Allerdings passe ich die Grenzen
> mittels eines LowPassFilters statt mit konstanter Schrittweite an.
Ich habe herausgefunden, dass je komplexer und "eigenständiger" so ein 
Filter ist, um so seltsamer sind die erzielbaren Effekte und 
Fehlfunktionen draußen im Feld. Und vor Allem: niemals wieder kann man 
diese Effekte oder die Fehlfunktionen im Labor nachstellen und 
untersuchen.

: Bearbeitet durch Moderator
von chris_ (Gast)


Lesenswert?

>Ich habe herausgefunden, dass je komplexer und "eigenständiger" so ein
>Filter ist, um so seltsamer sind die erzielbaren Effekte und
>Fehlfunktionen draußen im Feld. Und vor Allem: niemals wieder kann man
>diese Effekte oder die Fehlfunktionen im Labor nachstellen und
>untersuchen.

Ja, Filterentwurf ist ziemlich schwierig. Eigentlich muss man erst die 
Störungen genau analysieren, dann ein Modell des Signals erstellen und 
dann den Filter darauf anpassen. Mit jeder Filteraktion gehen natürlich 
Daten verloren, da sie weg gefiltert werden, deshalb wäre es besser, man 
hätte immer die Rohdaten. Aber es gibt eben auch Fälle, bei denen 
Ausreißer ziemlich offensichtlich sind und weggelassen werden können.

von Pandur S. (jetztnicht)


Lesenswert?

Ich wuerde mir erst mal Gedanken ueber den Unsprung der Ausreisser 
machen. Dann wuerde ich eine statistik aufnehmen, Fouriertransformieren 
und solches Zeug. Falls es tatsaechlich Ausreiiser sind, Wie zb 
kosmische Strahlung. Dann muesste man noch ein paar Werte weiter 
sampeln, bevor man den ausreisser als solchen erkennen kann. Das waere 
dann eine Verzoegerung von ein paar Samples. Wenn das System diese 
Massnahme verzeiht...

von Ingo L. (corrtexx)


Lesenswert?

Lothar M. schrieb:
> Nur weiß man gerade bei Ausreißern nicht, wie stark sie ausreißen.
> Und deshalb funktioniert ein Medianfilter tendenziell zuverlässiger als
> das Begrenzen von Werten jenseits des gewünschten/erwarteten/geplanten
> Bereichs.
Ich habe immer vor allen ADC-Kanälen einen analogen Tiefpass. Mit diesen 
Parametern und der dem Kennen des Eingangssignals lässt sich ermitteln 
wie schnell sich eine Signal von Sample zu Sample maximal ändern kann 
oder ob es sich hier um eine Störung handelt.

chris schrieb:
> Allerdings passe ich die Grenzen mittels eines LowPassFilters
Ich auch, mit nem analogen (RC) Tiefpass ;)

von Frank B. (frank501)


Lesenswert?

Vielleicht nicht das allerschnellste, aber für meine Verhältnisse 
ausreichend:

Ich schreibe die Sensordaten fortlaufend in ein Array mit 6 Feldern.{1}
Dieses Array kopiere ich in ein zweites, eben so großes Array und lasse 
einen Durchlauf eines Bubblesort durch laufen. Dadurch steht die größte 
Zahl ganz oben. {2}
Danach kommt ein umgekehrter Bubblesort wodurch die kleinste Zahl ganz 
unten steht. {3}
Die mittleren 4 Felder addiere ich {4} und teile das Ergebnis durch 4 
{5}
(2 mal rechts schieben erfüllt den selben Zweck, geht aber schneller, 
deshalb 6 Felder. Möglich sind auch 4 oder 10 Felder, Hauptsache man 
kann das Teilen durch einfaches rechtsverschieben ersetzen)

{1}  63, 54, 102, 59, 11, 61
{2}  54, 63, 59, 11, 61, 102
{3}  11, 54, 63, 59, 61, 102
{4}  54 + 63 + 59 + 61 = 237
{5}  237 / 4 = 59,25 (oder 237 shr 2 = 59)

Wenn natürlich mehrere Ausreisser in eine Richtung vorkommen, fliessen 
diese trotzdem in die Rechnung mit ein. Wenn man aber die Daten kennt 
und weiß, wie viele Ausreisser in Folge kommen können, kann man das Feld 
nach oben und unten noch erweitern. Dann muss man allerdings nicht nur 
zweimal sortieren sondern entsprechend öfter um die Maximal- und 
Minimalwerte aus der Mitte heraus zu bekommen.

Oder man lässt den Filter mehrmals über die Werte laufen, indem man die 
Ergebnisse des ersten Filters wiederum fortlaufend in ein Array schreibt 
und filtert.
Das erhöht dann die Latenz und die Gesamtlaufzeit des Filters natürlich 
mit jeder Filterstufe mehr als das Array zu erweitern.

von Lothar M. (Firma: Titel) (lkmiller) (Moderator) Benutzerseite


Lesenswert?

Frank B. schrieb:
> Dieses Array kopiere ich in ein zweites, eben so großes Array und lasse
> einen Durchlauf eines Bubblesort durch laufen. Dadurch steht die größte
> Zahl ganz oben. {2}
> Danach kommt ein umgekehrter Bubblesort wodurch die kleinste Zahl ganz
> unten steht. {3}
Du machst also nur 1 Durchlauf des Bubblesort in jede Richtung. Das ist 
eine Art "Medianfilter mit Abkürzung". Dabei verlässt du dich aber 
darauf, dass es keine 2 Ausreißer in die selbe Richtung gibt. Wenn 
deine Eingangsdaten so aussehen, ist das Ergebnis suboptimal:
{1} 63, 54, 102, 59, 111, 61

: Bearbeitet durch Moderator
von Yalu X. (yalu) (Moderator)


Lesenswert?

Wie schon geschrieben wurde, ist das Medianfilter ein sehr wirksames
Verfahren zur Elimination von Ausreißern. Im Gegensatz zum Tiefpass-
oder Mittelwertfilter dürfen die Ausreißer eine beliebig hohe Amplitude
haben, und die eigentlichen Messdaten werden kaum verwaschen.

Eine sinnvolle Fenstergröße für die Medianbildung ist 5, da damit bei
begrenztem Rechenaufwand auch zwei kurz aufeinanderfolgende Ausreißer
eliminiert werden. Drei Ausreißer innerhalb von fünf Werten in die
gleiche Richtung werden zwar nicht mehr erkannt, aber wenn sie so dicht
liegen, kann man sowieso kaum noch von Ausreißern sprechen.

Hier ist noch ein netter C-Ausdruck, der den Median der 5 Zahlen a, b,
c, d und e mit der minimalen Anzahl von Vergleichen (6) und ohne die
Verwendung temporärer Variablen ermittelt:

1
median5 = b < a ? d < c ? b < d ? a < e ? a < d ? e < d ? e : d
2
                                                : c < a ? c : a
3
                                        : e < d ? a < d ? a : d
4
                                                : c < e ? c : e
5
                                : c < e ? b < c ? a < c ? a : c
6
                                                : e < b ? e : b
7
                                        : b < e ? a < e ? a : e
8
                                                : c < b ? c : b
9
                        : b < c ? a < e ? a < c ? e < c ? e : c
10
                                                : d < a ? d : a
11
                                        : e < c ? a < c ? a : c
12
                                                : d < e ? d : e
13
                                : d < e ? b < d ? a < d ? a : d
14
                                                : e < b ? e : b
15
                                        : b < e ? a < e ? a : e
16
                                                : d < b ? d : b
17
                : d < c ? a < d ? b < e ? b < d ? e < d ? e : d
18
                                                : c < b ? c : b
19
                                        : e < d ? b < d ? b : d
20
                                                : c < e ? c : e
21
                                : c < e ? a < c ? b < c ? b : c
22
                                                : e < a ? e : a
23
                                        : a < e ? b < e ? b : e
24
                                                : c < a ? c : a
25
                        : a < c ? b < e ? b < c ? e < c ? e : c
26
                                                : d < b ? d : b
27
                                        : e < c ? b < c ? b : c
28
                                                : d < e ? d : e
29
                                : d < e ? a < d ? b < d ? b : d
30
                                                : e < a ? e : a
31
                                        : a < e ? b < e ? b : e
32
                                                : d < a ? d : a;

Die Idee ist nicht von mir, ich kann nur gerade die Webseite, von der
ich den Code geklaut habe, nicht mehr finden.

: Bearbeitet durch Moderator
von Frank B. (frank501)


Lesenswert?

Lothar M. schrieb:
> Dabei verlässt du dich aber
> darauf, dass es keine 2 Ausreißer in die selbe Richtung gibt.

In dem Fall ist das richtig.
Ich schrieb ja auch, das man das Array oben und unten erweitern kann. 
Dann muss man allerdings Bubblesort auch 2 oder mehrmals über die Daten 
laufen lassen, ja nachdem wie weit man es erweitert.
Das kommt ganz auf die Daten an und auf das Messintervall.



Yalu X. schrieb:
> Eine sinnvolle Fenstergröße für die Medianbildung ist 5

Ich habe mich bewusst für 6 Werte entschieden von denen ich 2 verwerfe 
und somit auf 4 Werte komme, die ich verarbeiten muss, damit ich nicht 
dividieren muss sondern das Ergebnis der Addition einfach nach rechts 
verschieben kann, weil das Programmspeicher und Rechenschritte spart. 
Denn einfache Schiebeoperationen können Mikrocontroller meist schneller 
erledigen als eine Division.
Aber ansonsten stimme ich Dir voll und ganz zu.

Frank

von chris_ (Gast)


Lesenswert?

Frank B. (frank501)
>Vielleicht nicht das allerschnellste, aber für meine Verhältnisse
>ausreichend:

>Ich schreibe die Sensordaten fortlaufend in ein Array mit 6 Feldern.{1}

Hallo Frank,

Dein Verfahren entspricht der "trimmean" Funktion in Matlab/Octave.

Du schneidest oben und unten einen Wert ab, also 100%/6.
1
octave:28> a
2
a =
3
4
    63    54   102    59    11    61
5
6
octave:29> trimmean(a,100/6)
7
ans =  59.250

Wenn ich die Erklärung auf der Matlab Homepage richtig verstehe, müsste 
man als Parameter zwar 2*100/6 angeben, aber in Octave funktioniert 
scheinbar mit 100/6.

http://de.mathworks.com/help/stats/trimmean.html

von sadf (Gast)


Lesenswert?

Um aus einer Menge Messwerte einen passenden zu finden: median
Um einen ausreisse ansonsten zu identifizieren: Alle Messwerte (bzw. 
eine ausreichend große Teilmenge) speichern, und alle wegwerfen die 
jenseits von x-Sigma vom Mittelwert entfernt sind. Das ersprt die ex 
ante Kenntnis von DIFMAX

von Yalu X. (yalu) (Moderator)


Lesenswert?

Frank B. schrieb:
> Yalu X. schrieb:
>> Eine sinnvolle Fenstergröße für die Medianbildung ist 5
>
> Ich habe mich bewusst für 6 Werte entschieden von denen ich 2 verwerfe
> und somit auf 4 Werte komme, die ich verarbeiten muss, damit ich nicht
> dividieren muss

Ja, wenn man die Ausreißersuche sowieso mit einer Mittelwertbildung
kombinieren will, sind 2+2**n Werte ideal.

Wenn man lieber ein reines Medianfilter ohne Mittelung will, ist eine
ungerade Anzahl von Werten aus zwei Grunden vorteilhaft:

- Der Median ist klar als einer der n Werte definiert und muss nicht
  erst noch durch Mittelung des Unter- und Obermedians berechnet werden.

- Bei einer monotonen Folge von Eingangswerten kommen diese (bis auf ein
  paar am Anfang und am Ende) unverändert am Ausgang des Filters wieder
  heraus. Das ist dann wichtig, wenn man zwar die Ausreißer entfernen,
  aber kleinere Schwankungen in den Messwerten weitgehend beibehalten
  und nicht einfach glattbügeln möchte.

von Georg (Gast)


Lesenswert?

Markus schrieb:
> welche Methoden verwendet ihr, um Ausreißer z.B. von einem Sensor weg zu
> filtern?

3 Sigma-Korrektur. Messwerte ausserhalb 3 Sigma werden gestrichen und 
die Standardabweichung neu berechnet, dann wieder die Ausreisser 
streichen usw. bis keine mehr auftreten.

Grundlage: es muss sich um eine Standardverteilung der Messwerte 
handeln. Ist das der Fall, kommen Messwerte ausserhalb der dreifachen 
Standardabweichung so extrem selten vor, dass man sie zu Messfehlern 
erklären kann bzw. muss.

Solche Messwerte haben überhaupt keinen Einfluss mehr, andere Filter wie 
Medianfilter leisten das nicht.

Georg

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.