Dieser Artikel wurde maschinell übersetzt.

Testlauf

Logistische Regressionsklassifizierung mit Multischwarmoptimierung

James McCaffrey

Laden Sie die Codebeispiele herunter

James McCaffreyEine der grundlegendsten Formen des maschinellen Lernens ist die logistische Regression (LR) Klassifikation. Das Ziel der LR-Klassifikation ist ein Modell zu erstellen, die eine Variable vorhersagt, die einen von zwei möglichen Werten annehmen können. Sie möchten z. B. vorherzusagen, die von zwei Kandidaten ein Wähler wählen ("Smith" = 0, "Jones" = 1) auf der Grundlage der Wähler Alters (x 1), sex (X 2) und Jahreseinkommen (X 3).

Wenn Y der vorhergesagte Wert ist, würde eine LR-Modell für dieses Problem Form erfolgen:

z = b0 + b1(x1) + b2(x2) + b3(x3)
Y = 1.0 / (1.0 + e^-z)

B0, b1, b2 und b3 sind Gewichte, die nur numerische Werte sind, die bestimmt werden muss. In Worten berechnen Sie einen Wert Z, der die Summe von input-Werte mal b-Gewichte, sowie eine Konstante b0, dann füttern den Z-Wert der Gleichung, die mathematische Konstante e verwendet. Es stellt sich heraus, dass Y immer zwischen 0 und 1. Wenn Y kleiner als 0,5 ist, schließen Sie die Ausgabe ist 0 und Y ist größer als 0,5 man schließen, dass der Ausgang 1 ist.

Z. B. Annahme, dass ein Wähler Alter 32, Sex ist männlich (-1) und jährliche Einkommen in Zehntausende von Dollar ist 48,0. Und nehme an b0 = 9,0, b1 = 8.0, b2 = 5.0 und b3 = 5,0. Dann Z = 9,0 + (8.0)(32) + (5.0)(-1) + (-5.0)(48.0) = 2,0 und damit Y = 1.0 / (1.0 + e ^ -2,0) = 0.88.

Da Y größer als 0,5 ist, würden Sie feststellen, dass der Wähler Kandidaten 1 ("Jones") abholt. Aber woher kommen die b-Gewicht-Werte? Ausbildung eine LR-Klassifizierung ist der Prozess der Werte für die b-Gewichte zu finden. Die Idee ist, verwenden Sie Trainingsdaten, die Ausgabewerte kennt und dann b Werte zu finden, so dass die Differenz zwischen der berechneten Ausgabewerte und die bekannten Ausgabewerte minimiert wird. Dies ist ein Mathe-Problem, die oft als Numerische Optimierungsverfahren bezeichnet wird.

Gibt es etwa ein Dutzend große Optimierungsalgorithmen in Computerlernen verwendet. Für die logistische Regression Klassifizierung Ausbildung, werden zwei der am häufigsten verwendeten Algorithmen iterative Newton-Raphson und L-BFGS bezeichnet. In diesem Artikel stelle ich eine Technik namens Multi-Schwarm Optimierung (MSO). MSO ist eine Variante des Particle Swarm Optimization (PSO). In MSO hat ein virtuelles Teilchen eine Position, die eine Reihe von b-Gewicht Werten entspricht. Ein Schwarm ist eine Sammlung von Teilchen, die in einer Weise inspiriert von Gruppenverhalten wie die Scharen von Vögeln zu verschieben. MSO unterhält mehrere Schwärme, die mit einander, im Gegensatz zu PSO zu interagieren, die nur ein Schwarm verwendet.

Ein guter Weg, um zu sehen, wohin dieses Artikels und bekommen eine Vorstellung davon, was LR mit MSO ist, ist ein Blick auf das Demoprogramm in Abbildung 1. Das Demoprogramm soll mithilfe von MSO um ein LR-Modell zu erstellen, das Y für eine Reihe von synthetischen (programmgesteuert generierten) Daten vorhersagt.

logistische Regression mit mehreren Schwarm Optimierung in Aktion
Abbildung 1 logistische Regression mit mehreren Schwarm Optimierung in Aktion

Das Demoprogramm beginnt, indem Sie 10.000 Zufallsdaten Elemente erstellen wo gibt es fünf Vorhersagedienst Variablen (oft als KEs in der ML-Terminologie). Jedes Feature-Wert liegt zwischen 10,0 und + 10,0 und der Y-Wert 0 oder 1, ist in der letzten Spalte des Datensatzes. Die Feature-Werte entsprechen nicht zu einem echten Problem.

Die 10.000-Artikel-Datensatzes gliedert sich nach dem Zufallsprinzip in ein 8.000-Element Ausbildungs-Set zur Erstellung der LR-Modell und ein 2.000-Element Hold-Out-Prüfgerät verwendet, um die Genauigkeit des Modells nach dem Training zu bewerten. Das Demoprogramm erstellt eine LR-Klassifizierung und anschließend vier Schwärme, jeweils mit drei Teilchen verwendet, um die Klassifizierung zu trainieren. MSO ist ein iterativer Prozess, und die maximale Anzahl von Iterationen, MaxEpochs, auf 100 festgelegt ist.

Die Demo zeigt den besten (kleinsten) Fehler gefunden durch jedes Partikel jeder 10 Epochen. Nach Abschluss der Ausbildung sind die besten Gewichte gefunden (4.09, 10.00, 8.43, 1.86,-9.27, 1,84). Verwenden diese Gewichte, die Genauigkeit der LR-Modells wird berechnet für die Trainingsdaten (99,98 Prozent korrigieren, das ist 7.998 von 8.000) und für die Testdaten (99,85 Prozent korrigieren, das ist 1.997 von 2.000). Die Genauigkeit des Modells mit den Testdaten gibt Ihnen eine grobe Annäherung wie gut das Modell tun würden, wenn neue Daten vorgelegt, das unbekannte Werte ausgeben.

Dieser Artikel setzt voraus, Sie haben zumindest fortgeschrittene Programmierkenntnisse, aber nicht annehmen, dass Sie wissen nichts über die logistische Regression Klassifizierung oder Multi-Schwarm-Optimierung. Das Demoprogramm ist codiert mit c# sollte nicht, aber Sie allzu große Schwierigkeiten, die Umgestaltung des Codes in eine andere Sprache wie Visual Basic .NET oder Python.

Der Demo-Code ist zu lang hier in seiner Gesamtheit vorstellen, aber der vollständige Quellcode ist verfügbar in den Codedownload zu diesem Artikel. Der Demo-Code enthält alle normalen Fehlerüberprüfung entfernt, die wichtigsten Ideen, die so klar wie möglich und die Größe des Codes klein zu halten.

Allgemeine Programmstruktur

Die gesamte Programmstruktur mit einigen geringfügigen Änderungen platzsparend, präsentiert sich in Abbildung 2. Um die Demo zu erstellen, ich Visual Studio gestartet und erstellt eine neue C#-Konsolenanwendung mit dem Namen LogisticWithMulti. Die Demo hat keine signifikante Microsoft .NET Framework Abhängigkeiten, damit aktuelle Version des Visual Studio funktioniert.

Abbildung 2: Allgemeine Programmstruktur

using System;
namespace LogisticWithMulti
{
  class LogisticMultiProgram
  {
    static void Main(string[] args)
    {
      Console.WriteLine("Begin demo");
      int numFeatures = 5;
      int numRows = 10000;
      int seed = 0;
      Console.WriteLine("Generating " + numRows +
        " artificial data items with " + numFeatures + " features");
      double[][] allData = MakeAllData(numFeatures, numRows, seed);
      Console.WriteLine("Done");
      Console.WriteLine("Creating train and test matrices");
      double[][] trainData;
      double[][] testData;
      MakeTrainTest(allData, 0.80, seed, out trainData, out testData);
      Console.WriteLine("Done");
      Console.WriteLine("Training data: ");
      ShowData(trainData, 4, 2, true);
      Console.WriteLine("Test data: ");
      ShowData(testData, 3, 2, true);
      Console.WriteLine("Creating Logistic Regression classifier");
      LogisticClassifier lc = new LogisticClassifier(numFeatures);
      int numSwarms = 4;
      int numParticles = 3;
      int maxEpochs = 100;
      Console.WriteLine("Setting numSwarms = " + numSwarms);
      Console.WriteLine("Setting numParticles = " + numParticles);
      Console.WriteLine("Setting maxEpochs = " + maxEpochs);
      Console.WriteLine("\nStarting training");
      double[] bestWeights = lc.Train(trainData, maxEpochs,
        numSwarms, numParticles);
      Console.WriteLine("Training complete");
      Console.WriteLine("Best weights found:");
      ShowVector(bestWeights, 4, true);
      double trainAcc = lc.Accuracy(trainData, bestWeights);
      Console.WriteLine("Accuracy on training data = " +
        trainAcc.ToString("F4"));
      double testAcc = lc.Accuracy(testData, bestWeights);
      Console.WriteLine("Accuracy on test data = " +
        testAcc.ToString("F4"));
      Console.WriteLine("End demo");
      Console.ReadLine();
    } // Main
    static double[][] MakeAllData(int numFeatures,
      int numRows, int seed) { . . }
    static void MakeTrainTest(double[][] allData, 
      double trainPct, int seed,
      out double[][] trainData, out double[][] testData) { . . }
    static void ShowData(double[][] data, int numRows,
      int decimals, bool indices) { . . }
    static void ShowVector(double[] vector, int decimals,
      bool newLine) { . . }
  } // Program
  public class LogisticClassifier { . . }
} // ns

Nach der Vorlagencode in den Visual Studio -Editor geladen, umbenannt, im Projektmappen-Explorer Fenster ich Datei Program.cs automatisch in die aussagekräftigeren LogisticMultiProgram.cs und Visual Studio umbenannt Klasse Programm für mich. An der Spitze des Quellcodes löschte ich alle using-Anweisungen, die auf nicht benötigte Namespaces verwiesen, so dass nur den Verweis auf die Top-Level-System-Namespace.

Die Program-Klasse hat Hilfsmethoden MakeAllData, machen­TrainTest, ShowData und ShowVector. Die gesamte logistische Regression Logik ist in einer einzigen LogisticClassifier-Klasse enthalten. Die LogisticClassifier-Klasse enthält geschachtelte Hilfsklassen Particle Swarm und MultiSwarm, MSO-Daten und Logik verwendet während des Trainings zu kapseln. Diese Hilfsklassen könnte außerhalb der LogisticClassifier-Klasse definiert haben.

Die Main-Methode hat eine Menge WriteLine Lärm. Die aufrufende Kernsätze sind recht einfach. Die synthetischen Daten erwirtschaftet werden, etwa so:

int numFeatures = 5;
int numRows = 10000;
int seed = 0; // Gives representative demo
double[][] allData = MakeAllData(numFeatures, numRows, seed);

Methode MakeAllData erstellt zufällige b-Gewicht Werte zwischen 10,0 und + 10,0 und dann für jedes Datenelement Zufallswerte X 10,0 bis + 10,0 sind generiert und mit der b-Gewicht-Werte, die dann verwendet werden, um Y-Werte zu generieren. Die synthetischen Daten entspricht einer Datengruppe, wo die X-Werte normalisiert wurden und es gibt ungefähr gleiche Grafen von Y = 0 und Y = 1 Werte.

Die Daten gliedert sich in die Ausbildung und Test-sets mit diesen Anweisungen:

double[][] trainData;
double[][] testData;
MakeTrainTest(allData, 0.80, seed, out trainData, out testData);

Das LR-Modell erstellt und trainiert mit folgenden Anweisungen:

LogisticClassifier lc = new LogisticClassifier(numFeatures);
int numSwarms = 4;
int numParticles = 3;
int maxEpochs = 100;
double[] bestWeights = lc.Train(trainData, 
  maxEpochs, numSwarms, numParticles);

Und die Genauigkeit des Modells wird mit diesen beiden Anweisungen ausgewertet:

double trainAcc = lc.Accuracy(trainData, bestWeights);
double testAcc = lc.Accuracy(testData, bestWeights);

Verständnis des MSO-Algorithmus

Hier ist die MSO-Optimierung in hochrangigen Pseudocode:

for-each swarm
  initialize each particle to a random position
end-for
for-each swarm
  for-each particle in swarm
    compute new velocity
    use new velocity to compute new position
    check if position is a new best
    does particle die?
    does particle move to different swarm?
  end-for
end-for
return best position found

Der wesentliche Teil der MSO-Algorithmus ist ein Teilchen Geschwindigkeit, computing, die nur einen Satz von Werten, die Steuern, wo ein Teilchen bewegen wird. Zum Beispiel für ein Problem mit nur zwei X-Maße, wenn ein Teilchen ist (6.0, 8.0) und die Geschwindigkeit ist (2.0, 1.0), neue Position des Partikels werden (4.0, 9.0).

Geschwindigkeit wird ermittelt, so dass ein Teilchen tendenziell in die aktuelle Richtung zu bewegen; neigt dazu, seine beste Platzierung bisher gefunden bewegen; tendenziell auf dem Weg zu der besten Position, die durch eines seiner Mitglieder Kollegen Schwarm gefunden; und neigt dazu, auf dem Weg zu der besten Position jedes Partikel in jedem Schwarm gefunden.

In mathematischen Begriffen wenn x(t) ein Teilchen Position zum Zeitpunkt t, dann eine neue Geschwindigkeit, ist v(t+1) wie folgt berechnet:

v(t+1) = w * v(t) +
         (c1 * r1) * (p(t) - x(t)) +
         (c2 * r2) * (s(t) - x(t)) +
         (c3 * r3) * (g(t) - x(t))

Begriff p(t) ist des Partikels bekannteste Position. Begriff s(t) ist die beste Position der jedes Partikel in der Partikel Schwarm. Term g(t) ist die beste Stellung auf dem Weltmarkt Teilchen jeder Schwarm. Begriff w ist eine Konstante, die den Trägheit-Faktor genannt. Begriffe-c1, c2 und c3 sind Konstanten, die eine maximale Änderung für jede Komponente der neuen Geschwindigkeit zu schaffen. Begriffe-r1, r2 und r3 und zufällige Werte zwischen 0 und 1, die eine Randomisierung Wirkung jedes Velocity Update bereitstellen.

Angenommen, ein Teilchen zurzeit ist (20,0, 30.0) und die aktuelle Geschwindigkeit (1,0, 3,0). Außerdem ist die bekannteste Position des Partikels (10.0, 12.0), ist die bekannteste Position jedes Partikel in der Schwarm (8.0, 9.0), und ist die bekannteste Position jedes Partikel in jedem Schwarm (5.0, 6.0). Und annehmen, ständige w Wert 0.7 hat, Konstanten c1 und c2 beide 1.4 sind und Konstante c3 0.4 ist. Schließlich angenommen, zufällige Werte r1, r2 und r3 sind alle 0,2.

Die neue Geschwindigkeit des Teilchens (mit Rundung auf eine Dezimalzahl) ist:

v(t+1) = 0.7 * (-1.0, -3.0) +
         (1.4 * 0.2) * ((10.0, 12.0) - (20.0, 30.0)) +
         (1.4 * 0.2) * ((8.0, 9.0) - (20.0, 30.0)) +
         (0.4 * 0.2) * ((5.0, 6.0) - (20.0, 30.0))
       = 0.7 * (-1.0, -3.0) +
         0.3 * (-10.0, -18.0) +
         0.3 * (-12.0, -21.0) +
         0.1 * (-15.0, -24.0)
       = (-8.8, -16.2)

Und so neue Position des Partikels ist:

x(t+1) = (20.0, 30.0) + (-8.8, -16.2)
       = (11.2, 13.8)

Das Diagramm in der Abbildung 3 zeigt den MSO-Vorgang für ein Problem mit zwei X-Werte, wimmelt drei von fünf Teilchen, und wo ist die optimale Position (0, 0). Die Grafik zeigt, wie das erste Partikel in jedem Schwarm schließt sich auf die optimale Position. Die Spiral-Bewegung ist charakteristisch für MSO.

der Multi Schwarm Optimierungsalgorithmus illustriert
Abbildung 3 der Multi Schwarm Optimierungsalgorithmus illustriert

In der MSO-Pseudocode kann ein Teilchen mit einigen niedrigen Wahrscheinlichkeit sterben. Wenn ein Partikel stirbt, wird es mit einem neuen Teilchen an eine zufällige Position ersetzt. Ein Partikel kann mit einiger Wahrscheinlichkeit gering einwandern. Wenn Einwanderung auftritt, wird ein Teilchen mit einem anderen Teilchen aus einem anderen Schwarm vertauscht. Die Tod und Einwanderung Mechanismen MSO ein Element des Zufalls hinzufügen und verhindern, dass den Algorithmus in eine nicht optimale Lösung stecken zu bleiben.

Umsetzung der logistischen Regression mit MSO

Die Definition der Methode Zug beginnt mit:

public double[] Train(double[][] trainData, int maxEpochs,
  int numSwarms, int numParticles)
{
  int dim = numFeatures + 1;
  double minX = -10.0;
  double maxX = 10.0;
  MultiSwarm ms = new MultiSwarm(numSwarms, numParticles, dim);
...

Die Dimension des Problems ist die Anzahl der Vorhersagedienst-Features sowie ein, um die b0-Konstante zu berücksichtigen. Variablen MinX und MaxX halten die kleinsten und größten Werte für jeden einzelnen Wert in ein Partikel-Objekt-Stellung-Array. Die LogisticClassifier-Klasse enthält eine geschachtelte MultiSwarm Klasse. Der MultiSwarm Klassenkonstruktor erstellt ein Array von Arrays von Partikel-Objekten, von denen jeder zunächst eine zufällige Position und eine zufällige Geschwindigkeit hat. Da die logistische Regression Error-Methode nicht direkt sichtbar, auf die geschachtelte Partikel-Definition ist, liefern nicht der MultiSwarm Konstruktor Fehlerwert für jedes Teilchen, also Methode Zug Fehlerinformationen fügt. Zuerst wird jedes Partikel einen Fehlerwert:

for (int i = 0; i < numSwarms; ++i)
{
  for (int j = 0; j < numParticles; ++j)
  {
    Particle p = ms.swarms[i].particles[j];
    p.error = Error(trainData, p.position);
    p.bestError = p.error;
    Array.Copy(p.position, p.bestPosition, dim);
...

Als nächstes werden die aktuellen Schwarm beste Fehler und die globale beste Fehler berechnet:

...
    if (p.error < ms.swarms[i].bestError) // Swarm best?
    {
      ms.swarms[i].bestError = p.error;
      Array.Copy(p.position, ms.swarms[i].bestPosition, dim);
    }
    if (p.error < ms.bestError) // Global best?
    {
      ms.bestError = p.error;
      Array.Copy(p.position, ms.bestPosition, dim);
    }
  } // j
} // i

Die wichtigste Trainingsprinzip Schleife ist bereit, etwa so:

int epoch = 0;
double w = 0.729; // inertia
double c1 = 1.49445; // particle
double c2 = 1.49445; // swarm
double c3 = 0.3645; // multiswarm
double pDeath = 1.0 / maxEpochs;
double pImmigrate = 1.0 / maxEpochs;
int[] sequence = new int[numParticles];
for (int i = 0; i < sequence.Length; ++i)
  sequence[i] = i;

Die Werte für die Konstanten w, c1 und c2 sind das Ergebnis der Nachforschungen PSO. Interessanterweise sind im Vergleich zu vielen numerischen Optimierungsalgorithmen, PSO und MSO relativ unempfindlich gegen die Werte für interne Magische Konstanten (freie Parameter oder hyper Parameter genannt) verwendet. Es gibt wenig verfügbare Forschung für die c3-Konstante, die die Tendenz eines Teilchens auf die bekannteste Position jedes Partikel in jedem Schwarm bisher festgestellten beeinflusst. Der Wert, den ich verwende, den 0.3645, ist der halbe Wert der Trägheit Konstante und ist gut für mich in der Praxis gearbeitet.

Das Sequenz-Array enthält Indizes der Trainingsdaten. Dieses Array wird verschlüsselt werden, so dass in jedem Schwarm Teilchen in einer anderen Reihenfolge in jeder Iteration der Schleife wichtigste Trainingsprinzip verarbeitet werden.

Der wichtigste Trainingsprinzip Schleife:

while (epoch < maxEpochs)
{
  ++epoch;
  // Optionally print best error here
  for (int i = 0; i < numSwarms; ++i) // Each swarm
  {
    Shuffle(sequence);
    for (int pj = 0; pj < numParticles; ++pj) // Each particle
    {
      int j = sequence[pj];
      Particle p = ms.swarms[i].particles[j];
...

Zu wissen, wann Training zu stoppen, ist eine der schwierigsten Herausforderungen in Maschinelles Lernen. Hier wird eine feste Anzahl, MaxEpochs, von Iterationen verwendet. Dies ist eine einfache Lösung, aber es gibt ein Risiko, das Sie nicht genug trainieren können. Oder Sie trainieren könnte zu viel, die in einem Modell, die die Trainingsdaten sehr gut führen würde passt, funktioniert aber schlecht auf neuen Daten. Dies nennt man übermäßig passend. Es gibt Dutzende von Techniken, die verwendet werden können, gegen übermäßige Anpassung.

Als nächstes die neue Geschwindigkeit nach dem aktuellen Teilchen berechnet wird, wie bereits erläutert (siehe Abbildung 4).

Abbildung 4 neue Velocity nach aktuellen Teilchen wird berechnet

for (int k = 0; k < dim; ++k)
{
  double r1 = rnd.NextDouble();
  double r2 = rnd.NextDouble();
  double r3 = rnd.NextDouble();
  p.velocity[k] = (w * p.velocity[k]) +
    (c1 * r1 * (p.bestPosition[k] - p.position[k])) +
    (c2 * r2 * (ms.swarms[i].bestPosition[k] - p.position[k])) +
    (c3 * r3 * (ms.bestPosition[k] - p.position[k]));
  if (p.velocity[k] < minX)
    p.velocity[k] = minX;
  else if (p.velocity[k] > maxX)
    p.velocity[k] = maxX;
} // k

Nachdem die Geschwindigkeit berechnet wird, wird jeden seiner Komponentenwerte überprüft, um festzustellen, ob der Betrag groß ist, und wenn also der Wert wieder gezügelt wird ist. Dadurch wird verhindert, dass ein Teilchen bewegen sehr großen Entfernung in jedem eine Iteration. Für einige ML-Trainings-Aufgaben Beseitigung der Velocity-Einschränkung wird angezeigt, um das Training zu beschleunigen, aber gibt es keine soliden Forschungsergebnissen, spezifische Ratschläge zu geben.

Als nächstes wird die neue Geschwindigkeit verwendet, um des aktuellen Teilchens Neupositionierung und zugehörigen Fehlermeldungen zu berechnen:

for (int k = 0; k < dim; ++k)
{
  p.position[k] += p.velocity[k];
  if (p.position[k] < minX)
    p.position[k] = minX;
  else if (p.position[k] > maxX)
    p.position[k] = maxX;
}

Nachdem das aktuelle Teilchen verschoben wurde, wird seine neue Fehler berechnet:

p.error = Error(trainData, p.position); // Expensive
if (p.error < p.bestError) // New best position for particle?
{
  p.bestError = p.error;
  Array.Copy(p.position, p.bestPosition, dim);
}

Das aktuelle Teilchen neue Fehler möglicherweise einen neuen Schwarm am besten oder global am besten:

if (p.error < ms.swarms[i].bestError) // New best for swarm?
{
  ms.swarms[i].bestError = p.error;
  Array.Copy(p.position, ms.swarms[i].bestPosition, dim);
}
if (p.error < ms.bestError) // New global best?
{
  ms.bestError = p.error;
  Array.Copy(p.position, ms.bestPosition, dim);
}

Nachdem das aktuelle Teilchen verschoben wurde, ist eine Option möglicherweise töten, dass Partikel und generieren ein neues. Wenn ein zufälliger Wert unter einigen kleinen Schwellenwert liegt, wird ein neues Teilchen generiert:

double p1 = rnd.NextDouble();
if (p1 < pDeath)
{
  Particle q = new Particle(dim); // A replacement
  q.error = Error(trainData, q.position);
  Array.Copy(q.position, q.bestPosition, dim);
  q.bestError = q.error;

Anstelle einer festen Wahrscheinlichkeit des Todes ist eine Alternative zu schrittweise zu erhöhen die Wahrscheinlichkeit des Todes, zum Beispiel:

double pDeath = (maxProbDeath / maxEpochs) * epoch;

Nachdem das Ersatz-Partikel erstellt wurde, kann diese Partikel, reines Glück, einen neuen Schwarm am besten oder global am besten:

if (q.error < ms.swarms[i].bestError) // Best swarm error by pure luck?
{
  ms.swarms[i].bestError = q.error;
  Array.Copy(q.position, ms.swarms[i].bestPosition, dim);
  if (q.error < ms.bestError) // Best global error?
  {
    ms.bestError = q.error;
    Array.Copy(q.position, ms.bestPosition, dim);
  }
}

Der Tod-Mechanismus schließt durch den Austausch von aktuellen Teilchen für den Ersatz, den aktuellen Partikel effektiv zu töten:

...
  ms.swarms[i].particles[j] = q;
} // Die

Als nächstes beginnt der (optionale) Einwanderung-Mechanismus:

double p2 = rnd.NextDouble();
if (p2 < pImmigrate)
{
  int ii = rnd.Next(0, numSwarms); // rnd swarm
  int jj = rnd.Next(0, numParticles); // rnd particle
  Particle q = ms.swarms[ii].particles[jj]; // q points to other
  ms.swarms[i].particles[j] = q;
  ms.swarms[ii].particles[jj] = p; // the exchange
...

Der Einwanderung-Mechanismus ist ziemlich roh. Der Code wählt einen zufälligen Schwarm und dann ein zufälliges Teilchen von dem Schwarm, und dann tauscht das zufällige Teilchen mit dem aktuellen Teilchen. Wie codiert, gibt es keine Garantie, dass das zufällig ausgewählte Teilchen in einem Schwarm das aktuelle Teilchen unterschiedlich sein wird.

Der Einwanderung-Mechanismus für Oberflächen von gucken ob tauschen Teilchen in zwei Schwärme ein oder zwei neue Schwarm-beste Positionen geführt:

...
  if (q.error < ms.swarms[i].bestError) // Curr has new position
  {
    ms.swarms[i].bestError = q.error;
    Array.Copy(q.position, ms.swarms[i].bestPosition, dim);
  }
  if (p.error < ms.swarms[ii].bestError) // Other has new position
  {
    ms.swarms[ii].bestError = p.error;
    Array.Copy(p.position, ms.swarms[ii].bestPosition, dim);
  }
} // Immigrate

Methode Zug schließt mit der Rückkehr der besten Position, die durch jedes Partikel gefunden:

...
      } // j - each particle
    } // i - each swarm
  } // while
  return ms.bestPosition;
} // Train

Der Rückgabewert ist ein Verweis auf ein Array, einen Satz von Gewichten der logistischen Regression. Eine kleinere Alternative zu verringern die Chancen für eine unerwünschte Nebenwirkung ist die Werte auf einem lokalen Array Kopieren und einen Verweis auf das lokale Array zurückgeben.

Zusammenfassung

Dieser Artikel und die zugehörigen Code sollten erhalten, einsatzbereit, wenn Sie die logistische Regression Einreihung Multi Schwarm Optimierung für Training erkunden wollen. MSO ist eigentlich mehr eine Meta heuristische als ein Algorithmus. Damit meine ich, dass MSO ist eine Reihe von Design-Prinzipien, die in vielfältiger Weise umgesetzt werden können. Es gibt Dutzende von Änderungen am grundlegenden MSO-Entwurf, den Sie untersuchen können.

Die logistische Regression ist eine der einfachsten Formen des maschinellen Lernens Klassifizierung. Für viele Probleme der Klassifikation funktioniert LR einfach nicht gut. Jedoch viele ML-Praktiker, mich eingeschlossen, in der Regel beginnen Untersuchung eine Klassifizierung-Problem mit LR und anspruchsvollere Techniken dann verwenden, wenn erforderlich.

Im Vergleich zu älteren, Kalkül-basierte Numerische Optimierungsverfahren Techniken wie Farbverlauf Abstieg und L-BFGS, basierend auf meiner Erfahrung, Training mit MSO tendenziell bessere ML Modelle zu produzieren, sondern MSO ist fast immer eine Größenordnung langsamer.


Dr. James McCaffrey arbeitet für Microsoft Research in Redmond, Washington  Er arbeitete an verschiedenen Microsoft-Produkten, einschließlich Internet Explorer und Bing. Dr. McCaffrey kann erreicht werden unter jammc@microsoft.com.

Unser Dank gilt den folgenden technischen Experten von Microsoft für die Durchsicht dieses Artikels: Todd Bello und Alisson Sol