create_class_svm
— Erzeugen einer Support-Vektor-Maschine zur Klassifikation von
Mustern.
create_class_svm( : : NumFeatures, KernelType, KernelParam, Nu, NumClasses, Mode, Preprocessing, NumComponents : SVMHandle)
create_class_svm
erzeugt eine Support-Vektor-Maschine,
welche zur Klassifikation von Mustern verwendet werden kann. Die
Dimension, aus denen ein Muster besteht, wird mit
NumFeatures
, die Anzahl der verschiedenen Klassen mit
NumClasses
angegeben.
Für ein binäres Klassifikationsproblem, in dem die Klassen linear separierbar sind, werden aus einem gegebenen Trainingsdatensatz die Merkmalsvektoren ausgewählt, die die optimal trennende Hyperebene zwischen den verschieden Klassen aufspannen. Optimal bedeutet hier, dass der Abstand zwischen den konvexen Hüllen der jeweiligen Datensätze maximal wird. Die Merkmalsvektoren, die am Rand liegen und die Hypereberne implizit aufspannen, werden Support-Vektoren (SV) genannt.
Die Klassifikation eines neuen Merkmalsvektors z erfolgt mit der Formel: Dabei sind die Support-Vektoren, kodiert ihre jeweilige Klassenzugehörigkeit () und sind die Gewichtskoeffizienten. Mit b wird der Abstand der Hyperebene zum Ursprung bezeichnet. Hierbei ist anzumerken, dass für die Klassifikation nur ein Bruchteil des originalen Datensatzes benötigt wird (: Anzahl der Support-Vektoren), der genau an der Hyperebene liegt. Deshalb werden die Datenvektoren, die keine Support-Vektoren sind, verworfen. Die Klassifikationsgeschwindigkeit hängt von der Auswertung des Skalarproduktes zwischen den Support-Vektoren und dem zu klassifizierenden Merkmalsvektor ab, und somit von der Länge des Merkmalsvektors und der Anzahl der Support-Vektoren.
Für Klassifikationsprobleme, bei denen die Klassen nicht linear
separierbar sind, wird der Algorithmus in zweierlei Art erweitert.
Erstens wird ein bestimmter Anteil von Fehlern (Überlappungen) durch
die Verwendung von Schlupfvariablen innerhalb des Trainings
ausgeglichen. Das bedeutet, dass die Gewichte () einen maximalen Wert nicht übersteigen. Um intuitiv die Anzahl
von Überlappungen einzustellen, wird die als Nu-SVM
bezeichnete Variante des Trainingsalgorithmus verwendet. Der
Regularisierungsparameter Nu
stellt eine obere Schranke für
Trainingsfehler und eine untere Schranke für den Anteil von SV
dar. Als Faustregel empfiehlt es sich, einen Wert für Nu
einzustellen, der den Anteil der anwendungsspezifisch erwarteten
Fehler entspricht, z.B. 0.01 (entsprechend 1% maximalem
Trainingsfehler). Es ist zu beachten, dass ein zu großer Wert für
Nu
zu einem unzulässigen Trainingsproblem führen kann,
und somit die SVM nicht trainiert werden kann (siehe
train_class_svm
für Details). Da dies aber erst während
des Trainings festgestellt werden kann, erfolgt eine
Fehlerbehandlung erst dort. In diesem Fall ist eine neue SVM mit
angepasstem Nu
zu erzeugen.
Zweitens ist es möglich, eine so genannte Kernelfunktion in dem Trainings- bzw. Klassifikationsalgorithmus zu verwenden, da zwischen Merkmalsvektoren ausschließlich Skalarprodukte berechnet werden. Das bedeutet, dass das Skalarprodukt durch eine Kernelfunktion ersetzt wird, die das Skalarprodukt implizit in einem höherdimensionalen Merkmalsraum ausführt. Ein im Ursprungsraum linear nicht separierbarer Datensatz wird mit einer passenden Kernelfunktion im höherdimensionalem Merkmalsraum linear separierbar.
Die entsprechende Kernelfunktion kann mit dem Parameter
KernelType
ausgewählt werden:
Für KernelType
= 'linear' wird das
ursprüngliche Skalarprodukt (wie in der Formel) verwendet. Dieser
Kernel sollte nur für linear separierbare Datensätze verwendet
werden. Der Parameter KernelParam
wird ignoriert.
Die Radiale Basis Funktion (KernelType
= 'rbf' )
stellt die beste Wahl für die Kernelfunktion dar, da mit ihr relativ
leicht gute Ergebnisse erzielt werden können. Sie ist
folgendermaßen definiert:
Dabei muss im Parameter KernelParam
der Wert von
eingestellt werden. Anschaulich bedeutet der
Wert, wie groß der Einfluss eines SV auf seine Umgebung ist. Ein zu
großer Wert (kleiner Einfluss auf die Umgebung) bedeutet, dass jeder
Trainingsvektor ein SV wird. Der Trainingsalgorithmus lernt den
Trainingsdatensatz “auswendig„, ist aber nicht in der Lage zu
generalisieren (Überanpassung). Zusätzlich dauern
Training und Klassifikation viel länger. Ein zu kleiner Wert von
führt dazu, dass wenige SV einen großen
Einfluss auf weit entfernte Bereiche haben (Unteranpassung). Ein
typisches Vorgehen bei der Ermittlung des optimalen ist es, von einem kleinen
-Nu
Paar auszugehen und die Werte
solange zu erhöhen, solange die Erkennungsraten sich verbessern.
Mit KernelType
= 'polynomial_homogeneous' oder
'polynomial_inhomogeneous' können Polynome als Kernel
ausgewählt werden. Sie sind folgendermaßen definiert:
Der Grad des Polynoms d muss in KernelParam
eingestellt
werden. Dabei ist zu beachten, dass Polynome zu hohen Grades (d >
10) zu numerischen Problemen führen können.
Eine Faustregel ist, dass der RBF-Kernel für die meisten
Klassifikationsprobleme eine gute Wahl darstellt und deshalb
ausschließlich verwendet werden soll. Nichtsdestotrotz erzeugen der
lineare und polynomielle Kernel in manchen Anwendungen gute
Klassifikationsergebnisse und können zum Vergleich ausprobiert
werden. Weiterhin ist zu beachten, dass nur für den RBF-Kernel der
Mode
'novelty-detection' und der Operator
reduce_class_svm
unterstützt werden.
Mit Mode
wird der generelle Klassifikationmodus angegeben,
was entweder beschreibt, wie das Multi-Klassen Problem auf binäre
Entscheidungen reduziert wird oder ob eine so genannte
'novelty-detection' Aufgabe gelöst werden soll.
Mode
= 'one-versus-all' erzeugt einen
Klassifikator für jede Klasse, die sie mit allen restlichen Klassen
vergleicht. In der Testphase wird die Klasse mit dem größten
Klassifikationsergebnis (siehe Klassifikationsformel ohne
Vorzeichen) ausgewählt. Mode
= 'one-versus-one'
erzeugt zwischen allen Paaren von Klassen jeweils einen
Klassifikator. In der Testphase erfolgt eine Abstimmung, bei der die
Klasse mit den meisten Stimmen ausgewählt wird. Die optimale
Strategie (Mode
) hängt von der Anzahl der Klassen bzw.
der Anwendung ab. Bei n Klassen erzeugt 'one-versus-all'
n Klassifikatoren und 'one-versus-one' n(n-1)/2. Bei
nur zwei Klassen erzeugt 'one-versus-one' genau einen
Klassifikator und 'one-versus-all' unnötigerweise zwei
symmetrische Klassifikatoren. Bei wenigen Klassen (ca. bis zu 10) ist
'one-versus-one' sowohl im Training als auch in der
Testphase schneller, da die Unterklassifikatoren weniger
Trainingsdaten enthalten und in der Summe weniger Support-Vektoren
entstehen. Für viele Klassen ist 'one-versus-all'
vorzuziehen, da die Anzahl der Klassifikatoren für
'one-versus-one' quadratisch wächst und daher unnötig
viele Sub-Klassifikatoren erzeugt werden.
Einen besonderen Fall stellt die Situation dar, falls nur die
Zugehörigkeit von Testdaten zu den Trainingsdaten bestimmt
werden soll (Mode
= 'novelty-detection' ),
d.h. NumClasses
muss auf 1 gesetzt sein.
Die separierende Hyperebene verläuft nun um die Trainingsdaten herum
und trennt hierbei implizit Trainingsdaten von der Umgebung. Der
Vorteil ist hierbei, dass eine explizite Angabe einer
Rückweisungsklasse entfällt, was in bestimmten Anwendungen wie
z.B. Texturklassifikation vorteilhaft ist. Die Support-Vektoren
sind hierbei Daten, die am äußeren Rand der Verteilung liegen. Der
Parameter Nu
bestimmt den Anteil an Ausreißern innerhalb
des Trainingsdatensatzes. Es ist zu beachten, dass bei der
Klassifikation im 'novelty detection' Modus die Klasse der
Trainingsdaten mit dem Index 1 und die Rückweisungsklasse
mit dem Index 0 zurückgegeben wird. Somit dient die erste Klasse
als Rückweisungsklasse. Im Gegensatz dazu ist bei der
Klassifikation mit MLP standardmäßig die letzte Klasse als
Rückweisungsklasse.
Das ist anders als bei den MLP, bei denen im Standardfall die letzte Klasse die Rückweisungsklasse wird.
Mit den Parametern Preprocessing
und NumComponents
kann eine Vorverarbeitung der Merkmalsvektoren festgelegt werden.
Für Preprocessing
= 'none' werden die
Merkmalsvektoren ohne Änderung an die SVM übergeben.
NumComponents
wird hier ignoriert.
Für alle anderen Werte von Preprocessing
wird aus dem
Trainingsdatensatz eine Transformation der Merkmale berechnet, die
sowohl beim Training als auch bei der späteren Klassifikation dazu
verwendet wird, die Merkmalsvektoren zu transformieren.
Für Preprocessing
= 'normalization' werden die
Merkmalsvektoren normalisiert. Im Falle eines polynomiellen Kernels
wird der minimale bzw. maximale Wert des Trainingsdatensatzes auf -1
bzw. +1 abgebildet. Im Falle eines RBF-Kernels wird normalisiert,
indem der Mittelwert aller Trainingsvektoren von den
Merkmalsvektoren abgezogen wird und die dadurch entstehenden
Merkmalsvektoren durch die Standardabweichung der jeweiligen
Komponente der Trainingsvektoren geteilt werden. Die transformierten
Merkmalsvektoren haben also einen Mittelwert von 0 und eine
Standardabweichung von 1 in jeder Komponente.
NumComponents
wird in beiden Fällen ignoriert. Diese
Transformation empfiehlt sich bei allen Daten, bei denen die
Komponenten der Merkmalsvektoren nicht in denselben Einheiten
gemessen werden (z.B. falls einige der Daten Grauwertmerkmale und
andere Regionenmerkmale sind, oder falls z.B. Regionenmerkmale wie
'circularity' (Einheit: Skalar) und 'area' (Einheit: Quadratpixel)
gemischt werden). Die Normalisierung sollte grundsätzlich
durchgeführt werden, um die numerische Stabilität während des
Trainings/Testens zu verbessern.
Für Preprocessing
= 'principal_components'
werden die Merkmalsvektoren einer Hauptachsentransformation
(principal component analysis, PCA) unterzogen. Die
Hauptachsentransformation normalisiert zunächst die
Merkmalsvektoren (s.o.). Danach wird eine orthogonale
Transformation (eine Rotation im Merkmalsraum) berechnet, die die
Trainingsvektoren dekorreliert. Nach der Transformation ist der
Mittelwert der Trainingsvektoren 0 und die Kovarianzmatrix der
Trainingsvektoren ist eine Diagonalmatrix. Die Transformation wird
so bestimmt, dass die transformierten Merkmale, die die größte
Variationsbreite aufweisen, als erstes in dem transformierten
Merkmalsvektor stehen. Dadurch kann erreicht werden, dass die
letzten Komponenten des Merkmalsvektors, die typischerweise stark
vom Rauschen beeinflusst werden, ohne großen Informationsverlust
weggelassen werden können. Mit NumComponents
wird
festgelegt, wie viele der transformierten Komponenten verwendet
werden sollen. Es können bis zu NumFeatures
Komponenten
selektiert werden. Mit Hilfe von get_prep_info_class_svm
kann der Informationsgehalt der einzelnen transformierten
Komponenten bestimmt werden und somit NumComponents
einfacher bestimmt werden. Wie die Normalisierung empfiehlt sich
diese Transformation, wenn die Merkmalsvektoren Mittelwerte und
Standardabweichungen haben, die sich stark von 0 bzw. 1
unterscheiden oder bei denen die Komponenten der Merkmalsvektoren
nicht in denselben Einheiten gemessen werden, und wenn zusätzlich
zu erwarten ist, dass die Merkmale stark korreliert sind. Hier ist
anzumerken, dass der RBF-Kernel bezüglich Dimensionsreduktion durch
die PCA sehr robust ist. Daher sollte er die erste Wahl sein, wenn
es darum geht, die Klassifikationszeiten zu beschleunigen.
Mit Preprocessing
= 'canonical_variates'
(kanonische Merkmale) wird eine Transformation bestimmt, die die
Trainingsvektoren zuerst normalisiert und dann im Mittel über alle
Klassen dekorreliert. Gleichzeitig werden in den transformierten
Trainingsvektoren die Mittelwerte der einzelnen Klassen möglichst
weit separiert. Wie bei Preprocessing
=
'principal_components' werden die transformierten
Komponenten nach Informationsgehalt sortiert, so dass transformierte
Merkmale mit wenig Informationsgehalt weggelassen werden können.
Bei kanonischen Merkmalen können höchstens
min(NumClasses
- 1,
NumFeatures
) Merkmale selektiert werden. Auch hier kann
mit get_prep_info_class_svm
der Informationsgehalt der
einzelnen transformierten Komponenten bestimmt werden. Wie die
Hauptachsentransformation können die kanonischen Merkmale dazu
verwendet werden, die Datenmenge ohne großen Informationsverlust zu
verringern, wobei zusätzlich noch die Trennbarkeit der Daten nach
der Datenreduktion optimiert wird.
Für die letzten zwei Transformationsarten
('principal_components' und 'canonical_variates' )
bestimmt NumComponents
die Länge des transformierten
Datenvektors, während NumFeatures
die Dimensionalität der
Eingabedaten (Länge des untransformierten Merkmalsvektors)
bestimmt. Dadurch wird die Länge der Eingabevariablen der SVM
geringer, wodurch sich normalerweise die Trainingszeit und die
Klassifikationszeit verringert.
Nachdem die SVM mit create_class_svm
erzeugt wurde, werden
typischerweise mit add_sample_class_svm
oder
read_samples_class_svm
Trainingsdaten hinzugefügt und die
SVM mit train_class_svm
trainiert. Daraufhin kann die SVM
mit write_class_svm
abgespeichert werden. Alternativ
können auch sofort nach dem Training Daten mit
classify_class_svm
klassifiziert werden.
Ein Vergleich zwischen SVM und mehrschichtigem Perzeptron (engl.:
multilayer perceptron, MLP; siehe create_class_mlp
) zeigt
typischerweise, dass SVMs generell schneller traniert werden,
insbesondere bei großen Trainingsdatensätzen, und eine leicht
verbesserte Erkennungsrate haben. Das MLP weist schnellere
Klassifikationszeiten auf und sollte daher in zeitkritischen
Anwendungen verwendet werden. Es ist zu beachten, dass der Vergleich
von optimal abgestimmten Parametern ausgeht.
Dieser Operator liefert ein Handle zurück. Es ist zu beachten, dass der Zustand einer Instanz dieses Handletyps durch bestimmte Operatoren geändert werden kann, obwohl das Handle als Eingabeparameter in diesen Operatoren verwendet wird.
NumFeatures
(input_control) integer →
(integer)
Anzahl der Eingabevariablen (Merkmale) der SVM.
Defaultwert: 10
Wertevorschläge: 1, 2, 3, 4, 5, 8, 10, 15, 20, 30, 40, 50, 60, 70, 80, 90, 100
Restriktion: NumFeatures >= 1
KernelType
(input_control) string →
(string)
Art des Kernels.
Defaultwert: 'rbf'
Werteliste: 'linear' , 'polynomial_homogeneous' , 'polynomial_inhomogeneous' , 'rbf'
KernelParam
(input_control) real →
(real)
Zusätzlicher Parameter für die Kernel Funktion. Im Falle des RBF-Kernels der Wert für . Falls polynomieller Kernel ausgewählt wurde, der Grad des Polynoms.
Defaultwert: 0.02
Wertevorschläge: 0.01, 0.02, 0.05, 0.1, 0.5
Nu
(input_control) real →
(real)
Regularisierungskonstante der SVM.
Defaultwert: 0.05
Wertevorschläge: 0.0001, 0.001, 0.01, 0.05, 0.1, 0.2, 0.3
Restriktion: Nu > 0.0 && Nu < 1.0
NumClasses
(input_control) integer →
(integer)
Anzahl der Klassen.
Defaultwert: 5
Wertevorschläge: 2, 3, 4, 5, 6, 7, 8, 9, 10
Restriktion: NumClasses >= 1
Mode
(input_control) string →
(string)
Modus der SVM.
Defaultwert: 'one-versus-one'
Werteliste: 'novelty-detection' , 'one-versus-all' , 'one-versus-one'
Preprocessing
(input_control) string →
(string)
Art der Vorverarbeitung (Transformation) der Merkmalsvektoren.
Defaultwert: 'normalization'
Werteliste: 'canonical_variates' , 'none' , 'normalization' , 'principal_components'
NumComponents
(input_control) integer →
(integer)
Parameter der Vorverarbeitung: Anzahl der
transformierten Merkmale (ignoriert bei
Preprocessing
= 'none' und
Preprocessing
= 'normalization' ).
Defaultwert: 10
Wertevorschläge: 1, 2, 3, 4, 5, 8, 10, 15, 20, 30, 40, 50, 60, 70, 80, 90, 100
Restriktion: NumComponents >= 1
SVMHandle
(output_control) class_svm →
(handle)
Handle der SVM.
create_class_svm (NumFeatures, 'rbf', 0.01, 0.01, NumClasses,\ 'one-versus-all', 'normalization', NumFeatures,\ SVMHandle) * Generate and add the training data for J := 0 to NumData-1 by 1 * Generate training features and classes * Data = [...] * Class = ... add_sample_class_svm (SVMHandle, Data, Class) endfor * Train the SVM train_class_svm (SVMHandle, 0.001, 'default') * Use the SVM to classify unknown data for J := 0 to N-1 by 1 * Extract features * Features = [...] classify_class_svm (SVMHandle, Features, 1, Class) endfor
Sind die Parameterwerte korrekt, dann liefert
create_class_svm
den Wert 2 (H_MSG_TRUE). Gegebenenfalls wird eine
Fehlerbehandlung durchgeführt.
read_dl_classifier
,
create_class_mlp
,
create_class_gmm
clear_class_svm
,
train_class_svm
,
classify_class_svm
Bernhard Schölkopf, Alexander J.Smola: „Learning with Kernels“;
MIT Press, London; 1999.
John Shawe-Taylor, Nello Cristianini: „Kernel Methods for Pattern
Analysis“; Cambridge University Press, Cambridge; 2004.
Foundation