kramann.info
© Guido Kramann

Login: Passwort:










13.6.1 Implementierung und Test der Klasse FuzzyRegler

Fuzzy-Regeln

  • Wie können die Fuzzy-Regeln in einer Klasse repräsentiert sein?
  • Dazu folgen hier noch einmal die Hinweise aus Aufgabe 2 der letzten Übung:
  • Ein Fuzzy-Regler kann nicht nur mehrere Fuzzy-Eingangssets haben, sondern auch mehrere Fuzzy-Ausgangssets.
  • Jedoch läßt sich gerade hier eine Reduktion der Komplexität erreichen, indem man bei einem Fuzzy-Ausgangsset pro Regler bleibt und einfach mehrere Regler formuliert, wenn es mehrere Ausgänge gibt.
  • Beachten Sie desweiteren, dass es im Allgemeinen zwar UND und ODER Verknüpfungen von Fuzzy-Eingangsgrößen bei den Fuzzy-Regeln gibt, aber die Behandlung der UND-Verknüpfung in der Regel ausreicht, indem man einfach Regeln zuläßt, die nur einen Eingang berücksichtigen und auf den gleichen Ausgang einwirken dürfen.
  • Somit reicht es in den Regeln n=1..k Eingangsgrößen zu berücksichtigen, die UND-verknüpft werden, wobei n==1 ein Sonderfall ist, bei dem nichts da ist, was mit der einen Eingangsgröße UND-verknüpft werden kann.
  • Der Einfachheit halber wird als Datentyp zur Repräsentation der Regeln ein zweidimensionales Integer-Array gewählt.
  • Jedes eindimensionale Array darin entspricht einer Fuzzy-Regel.
  • Ein Regel-Array besteht aus folgenden Einträgen:
  • Integer-Array-Wert bei Index 0: Index der Ausgangs-Fuzzy-Größe, auf die die Regel wirken soll.
  • Integer-Array-Wert bei Index 1,3,5,7, usw.: Index desjenigen Fuzzy-Eingangs-Sets, aus dem eine Fuzzy-Größe zur UND-Verknüpfung genommen werden soll.
  • Integer-Array-Wert bei Index 2,4,6,8, usw.: Index derjenigen Fuzzy-Größe, aus dem im vorhergehenden Index bezeichneten Fuzzy-Eingangs-Sets, das UND-Verknüpft werden soll.

Der Preis für die Kompaktheit der Regelrepräsentation ist, dass ihre Darstellung etwas kryptisch sind. Man könnte alternativ beispielsweise eine Hilfsklasse "Regel" einführen, die dann besser lesbare Bezeichner enthält. Hier soll darauf verzeichtet werden und ausgleichend einige Beispiele aus dem "Lüfter-Fuzzy-Regler" zum besseren Verständnis angeführt werden:

  • Der "Lüfter-Fuzzy-Regler" bestand aus zwei Fuzzy-Eingangs-Sets mit den Fuzzy-Größen [RK,RG] (Index 0) und [LK,LG] (Index 1), sowie dem Ausgangs-Fuzzy-Set bestehend aus den Fuzzy-Größen [VN,VK,VG].
  • Eine Regel lautete: WENN RK UND LK, DANN Ventilator auf VN, die Array-Repräsentation wäre: 0, 0,0, 1,0.
  • Eine Regel lautete: WENN RK UND LG, DANN Ventilator auf VK, die Array-Repräsentation wäre: 1, 0,0, 1,1.
  • Eine Regel lautete: WENN RG UND LK, DANN Ventilator auf VG, die Array-Repräsentation wäre: 2, 0,1, 1,0.
  • Eine Regel lautete: WENN RG UND LG, DANN Ventilator auf VG, die Array-Repräsentation wäre: 2, 0,1, 1,1.
  • Der Einfachheit halber werden die Regeln in der Klasse FuzzyRegeln einfach mit setRegeln(int[][] ) von außen gesetzt.
  • Da dann auch nicht viel Inhalt für die Klasse FuzzyRegeln übrigbleibt, wird auf sie vollends verzeichtet und ein Array, das die Regeln repräsentiert gleich in die KLasse FuzzyRegler integriert.
  • In der main-Methode am Ende der Klasse wird das "Lüfter-Beispiel" aus der Vorlesung durchgespielt.
public class FuzzyRegler
{
    private FuzzyEingangsSet[] fes = null;
    private FuzzyAusgangsSet   fas = null;
    private int[][] regeln;   
    public void setFuzzyEingangsSet(FuzzyEingangsSet[] fes)
    {
        this.fes = fes;
    }
    public void setFuzzyAusgangsSet(FuzzyAusgangsSet fas)
    {
        this.fas = fas;
    }
    public void setFuzzyRegeln(int[][] regeln)
    {
        this.regeln = regeln;
    }
    public double berechneAusgang(double[] eingang)
    {
        double ergebnis = 0.0;
        double gesamtflaeche = 0.0;
        for(int i=0;i<regeln.length;i++)
        {
             double aktivierung = 1.0; //zunächst auf Maximalwert setzen.
             //Alle Eingangsgrößen der aktuellen Regel durchgehen
             for(int k=0;k<(regeln[i].length-1)/2;k++) 
             {
                 //Minimum der Zugehörigkeitsgrade finden:
                 double neue_aktivierung = 
                 fes[regeln[i][1+k*2]].getZugehoerigkeitsgrad(regeln[i][2+k*2],eingang[regeln[i][1+k*2]]);                
                 if(neue_aktivierung < aktivierung)
                     aktivierung = neue_aktivierung;
             }
             //Mit gefundenem Aktivierungsgrad der aktuellen Regel in das Ausgangs-Fuzzy-Set gehen und
             //dort daraus resultierende Fläche und Schwerpunktlage berücksichtigen:
             double flaeche = fas.getFlaeche(regeln[i][0],aktivierung);             
             ergebnis+=flaeche*fas.getSchwerpunkt(regeln[i][0],aktivierung);
             gesamtflaeche+=flaeche;
        }
        return ergebnis/gesamtflaeche;
    }
    //Umsetzung des Lüfter-Beispiels zur Kontrolle:
    public static void main(String[] args)
    {
        //1. Fuzzy-Regler erstellen:
        FuzzyRegler fuzzyregler = new FuzzyRegler(); 
        //2. Fuzzy-Eingangs-Sets erstellen:
        FuzzyEingangsSet[] fes = new FuzzyEingangsSet[2];
        FuzzyEingangsSet   raumtemperatur   = new FuzzyEingangsSet();
        raumtemperatur.erzeugeFuzzyGroessen(2);
        raumtemperatur.verteileFuzzyGroessenGleichmaessig(10.0,30.0);
        FuzzyEingangsSet   luftfeuchtigkeit = new FuzzyEingangsSet();
        luftfeuchtigkeit.erzeugeFuzzyGroessen(2);
        luftfeuchtigkeit.verteileFuzzyGroessenGleichmaessig(50.0,70.0);
        fes[0] = raumtemperatur;        
        fes[1] = luftfeuchtigkeit;        
        fuzzyregler.setFuzzyEingangsSet(fes);
        //3. Fuzzy-Ausgangs-Set erstellen:
        FuzzyAusgangsSet fas = new FuzzyAusgangsSet();
        fas.erzeugeFuzzyGroessen(3+2); //Drei Fuzzygrößen und Minimum und Maximum
        fas.verteileFuzzyGroessenGleichmaessig(-100.0,300.0);
        fuzzyregler.setFuzzyAusgangsSet(fas);
        //4. Fuzzy-Regeln hinzufügen:
        int[][] regeln = new int[4][];
        regeln[0] = new int[] {0, 0,0, 1,0};
        regeln[1] = new int[] {1, 0,0, 1,1};
        regeln[2] = new int[] {2, 0,1, 1,0};
        regeln[3] = new int[] {2, 0,1, 1,1};
        fuzzyregler.setFuzzyRegeln(regeln);
        //Einige Ausgangsgrößen zum Test bestimmen:
        System.out.println("Eingang: T=25 A=60, Sollausgang: 144.737, es ergibt sich:"
        +fuzzyregler.berechneAusgang(new double[] {25.0,60.0}));
        System.out.println("Eingang: T=50 A=100, Sollausgang: 200, es ergibt sich:"
        +fuzzyregler.berechneAusgang(new double[] {50.0,100.0}));
        System.out.println("Eingang: T=20 A=60, Sollausgang: 125, es ergibt sich:"
        +fuzzyregler.berechneAusgang(new double[] {20.0,60.0}));
        System.out.println("Eingang: T=25 A=70, Sollausgang: 168.182, es ergibt sich:"
        +fuzzyregler.berechneAusgang(new double[] {25.0,70.0}));
    }
}

Code 13.6.1-1: Die Klasse FuzzyRegler.

fuzzy_java3.zip - Download der Klasse FuzzyRegler und aller Hilfsklassen.