it-swarm.com.de

Kalender / Planungsalgorithmus

Ich stehe vor einem Problem. Ich bin mir nicht sicher, wie ich mich nähern soll. Ich muss einen Kalender für Mitarbeiter erstellen, von denen jeder bestimmte Arbeitsbeschränkungen hat (einige persönlich, andere häufig).

Womit ich arbeite :

  • Ich habe Ärzte
  • Jeder Arzt muss 5 Tage/Woche arbeiten.
  • Jeder Arzt muss 1 Nacht/Woche arbeiten
  • Jeder Arzt muss im Vergleich zu anderen Ärzten gleich viele Nächte arbeiten (oder so nah wie möglich).
  • Jeder Arzt muss die gleiche Anzahl von Donnerstag- und Sonntagabenden arbeiten wie andere Ärzte (oder so nah wie möglich).
  • Einige Ärzte können bestimmte Tage/Nächte nicht arbeiten (Eingabe durch den Benutzer)
  • Einige Ärzte möchten bestimmte Tage/Nächte arbeiten (Eingabe durch den Benutzer)
  • Einige Ärzte möchten bestimmte Tage/Nächte nicht arbeiten (Eingabe durch den Benutzer)

Der betreffende Benutzer ist die Person, die sich mit dem Kalender befasst. Ich versuche, eine Lösung zu erstellen, die automatisch einen Kalender generiert, der alle Einschränkungen erfüllt. Die Lösung ist nur eine große Eingabe von "Ärzte hinzufügen" und "Einschränkungen hinzufügen" für jeden Arzt, dann eine Schaltfläche "Kalender generieren". Es ist wirklich einfach für den Benutzer.

Mein Problem :

Ich bin mir nicht sicher, wie ich die eigentliche Planung erstellen soll. Ich habe über neuronale Netze, genetische Algorithmen usw. gelesen und sie scheinen alle die richtige Lösung zu sein, aber auch nicht wirklich.

Wenn ich mir GAs anschaue, werden sie dazu gebracht, eine Lösung für eine bestimmte Population (mein Problem) zu finden, aber die Startpopulation muss bereits die angegebenen Einschränkungen einhalten, die dann optimiert werden. In diesem Fall ist meine Startpopulation bereits die Lösung. Ich brauche es nicht, um "optimiert" zu werden. Es spielt keine Rolle, dass eine einzelne Person 3 Montagabende hintereinander arbeitet, solange dies tatsächlich korrekt ist und andere die gleiche Menge arbeiten. Das bedeutet, dass andere irgendwann auch 3 Montagabende arbeiten und es in Ordnung ist. Das lässt mich denken, dass GAs für mich zu "fortgeschritten" sind, da mein Problem bereits mit dem Ausgangspunkt einer GA gelöst ist.

Aber andererseits sehen GAs wirklich so aus, als wären sie dafür gemacht, also verstehe ich es vielleicht nicht richtig?

Da ich noch nie GAs (oder neuronale Netze oder ähnliches) verwendet habe, möchte ich sicher sein, dass ich den richtigen Ansatz wähle, bevor ich mich auf eine solche Lernkurve einlasse.

Meine Frage :

Was ist Ihrer Meinung nach ein guter Ansatz/Algorithmus/Technik für ein Problem wie das meine? Gas? Neuronale Netze? Noch etwas ganz anderes?

Ich bin ganz Ohr und offen für weitere Details, wenn nötig, aber ich denke, ich habe mich ziemlich klar ausgedrückt :)

24
Gil Sand

Genetische Algorithmen und neuronale Netze sind hier nicht geeignet. Sie sind Meta-Heuristiken, um eine hinreichende, ungefähre Lösung für ein Problem zu finden. In beiden Fällen müssen Sie eine Kostenfunktion finden, um mögliche Lösungen zu bewerten. Sobald Sie über eine solche Kostenfunktion verfügen, ist es möglicherweise einfacher, manuell einen Algorithmus zu entwickeln, der für diese Kosten optimiert ist.

Dies ist ein wichtiger Gedanke: Bei zwei Zeitplänen müssen wir entscheiden, ob Zeitplan A oder Zeitplan B „besser“ ist. Sie haben verschiedene Kriterien aufgelistet, aber es ist nicht klar, wie sie zusammenhängen. Erfüllt die Nichterfüllung eines Kriteriums die gesamte Lösung? Oder macht das teilweise Versagen einer Einschränkung sie nur zu einer schlechteren Lösung als andere?

Auf der einfachsten Ebene können Sie die Woche einfach in diskrete Zeitfenster unterteilen und alle Slot-Doctor-Kombinationen brutal erzwingen. Sie können jedoch fehlerhafte Einschränkungen verwenden, um diesen Suchbereich auf eine überschaubare Größe zu reduzieren. Die Einschränkungen der Arbeitszeit und der Nachtschichten scheinen für eine solche Begrenzung des Suchraums geeignet zu sein. Sie haben dann Hunderte von Lösungskandidaten.

Um die beste Kandidatenlösung auszuwählen, müssen Sie sie bewerten. Dies ist ziemlich einfach, wenn eine weiche Einschränkung einen klaren Vorrang vor allen anderen weichen Einschränkungen hat, z. Wenn ein Arzt eine bestimmte Schicht nicht arbeiten kann, ist dies wichtiger als ein Arzt, der diese Schicht nicht arbeiten möchte. Aber ich kann diese Regeln nicht für Sie festlegen - das ist eine Managemententscheidung. Es ist schwieriger, wenn zwei weiche Einschränkungen keine eindeutige Priorität haben. In diesem Fall müssen Sie eine Art Kostenfunktion entwickeln, die die Bedeutung von zwei Einschränkungen in einer einzelnen Metrik vereinheitlicht.


Ich würde wahrscheinlich einen gierigen Algorithmus konstruieren, der einen leeren Zeitplan nach einigen priorisierten Kriterien ausfüllt. Dies ist vielleicht nicht die optimalste Lösung, aber es ist viel einfacher als zu philosophieren, was „optimal“ eigentlich bedeutet.

Als ersten Schritt könnten Sie die Nachtschichten an Wochenenden ausfüllen und versuchen, diejenigen Ärzte auszuwählen, die am längsten keine Nachtschicht am Wochenende durchgeführt haben, und dabei auch die Benutzerwünsche „Ich kann dort nicht arbeiten“ berücksichtigen . Unter der Annahme, dass diese Wünsche pro Woche und nicht kontinuierlich sind, bedeutet dies, dass nächste Woche ein Arzt ausgewählt wird, der eine Woche lang nicht am Wochenende arbeiten kann.

Ein ähnliches Verfahren kann für die anderen Nächte angewendet werden: Nachdem Sie versucht haben, die Wünsche der Benutzer zu respektieren, geben Sie Ärzte ein, je nachdem, wer die längste Zeit keine Nachtschicht gemacht hat. Die Prozedur wiederholt sich ähnlich für die dritte Art von Zeitfenster, die Tagesverschiebung. Wenn zwei Benutzerwünsche nicht in Einklang gebracht werden können, können Sie nachverfolgen, wie oft ein Benutzerwunsch gewährt wurde, und dann dem Arzt Prioritäten mit weniger gewährten Wünschen setzen.

Leider sehe ich einige Möglichkeiten, dieses System zu spielen: z. Wenn ein Arzt ausgewählt würde, um eine Wochenendnachtschicht zu arbeiten, aber eine Anfrage „Kann dort nicht arbeiten“ einreicht, würde sich seine Auswahl um eine Woche verzögern - was die Häufigkeit von Wochenendnachtschichten auf Kosten seiner Kollegen verringert. Wenn ein Wunschauflösungsverfahren implementiert ist, das die Anzahl der abgelehnten Anforderungen berücksichtigt, kann ein Benutzer einige unmögliche Anforderungen eingeben, um eine Anforderung zu verstärken, die er durchlaufen möchte. Unter der Annahme von Treu und Glauben (und der Flexibilität der Ärzte, Verschiebungen untereinander auszutauschen) sollte ein solcher Algorithmus jedoch zu einer ausreichend guten Lösung führen.

14
amon

Sie können simuliertes Tempern verwenden.

Ich habe so etwas gemacht, bevor ich meinen ersten Job bekommen habe - siehe https://vimeo.com/20610875 (Demo ab 2:50, Algorithmus erklärt ab 6:15).

Simuliertes Tempern ist eine Art genetischer Algorithmus, und vielleicht war es theoretisch nicht geeignet (wie @amon in seine Antwort behauptet), aber es hat in der Praxis sehr gut funktioniert und es war ungefähr die gleiche Verwendung Fall wie bei Ihnen.

Quellcode ist verfügbar (C #), aber obwohl es funktioniert, ist es schrecklich, fürchte ich, es war vor ein paar Jahren und als Autodidakt wusste ich nichts über Wartbarkeit. Es lieferte jedoch sehr gute Ergebnisse.

Wie es sowieso auf den Punkt gebracht funktioniert:

  • Generieren Sie einen 1 möglichen (möglicherweise nicht sehr guten, aber physikalisch möglichen) Zeitplan als Ausgangspunkt. Ein genetischer Algorithmus ist zu diesem Zeitpunkt nicht erforderlich - Sie können sich einfach brutal auf den Weg zur ersten Lösung machen, die Sie finden können. Ich habe Backtracking verwendet. Die Komplexität der Berechnungen kann überwunden werden, indem die Rota für jeden Tag separat gelöst wird. Wenn es überhaupt keine Lösung gibt (je nach Fall), erkennen Sie sie an diesem Punkt.

  • Erstellen Sie einen Lösungspool - beispielsweise 100 Kopien dieser Einstiegslösung.

  • Mutieren Sie jede Lösung nach dem Zufallsprinzip: Lassen Sie die Ärzte die Schichten untereinander tauschen, nehmen Sie einen zufälligen Arzt aus der Schicht und stellen Sie eine zufällig verfügbare Person darauf usw.

  • Bewerten Sie jede Lösung mit einem Fitnessfunktion , das bestimmt, wie gut sie ist. Ein Mann arbeitet mehr Nächte als ein anderer? Strafpunkte abziehen. Jemand wollte Montag machen, aber sie tun es nicht? Strafpunkte erneut abziehen.

  • Nehmen Sie - sagen wir - 20 beste Lösungen und kopieren Sie jede von ihnen fünfmal, wobei Sie die verbleibenden 80 mit ihnen überschreiben und sie so zur nächsten Generation übertragen. Überleben der Stärksten.

  • Spülen & wiederholen.

Die Zahlen sind offensichtlich willkürlich. Möglicherweise müssen Sie mit den Parametern herumspielen, um die optimalen Einstellungen für Ihr Szenario zu ermitteln.

Was das Mutieren einer Lösung betrifft, führt das simulierte Tempern etwas ein, das als Temperatur bezeichnet wird. Grundsätzlich bedeutet dies, dass Sie Ihre Lösungen am Anfang ziemlich stark mutieren sollten (z. B. immer 10 Versuche, Schichten auf einmal zu tauschen) und bei nachfolgenden Iterationen allmählich weniger aggressiv werden sollten, damit sie eher zu einer Feinabstimmung werden (z. B. nach unten) auf nur 2 versuchte Optimierungen pro Generation).

12
Konrad Morawski

Genetics Algorithms gelten hier. Während meines Grundstudiums schrieb einer meiner Kollegen eine Arbeit zu einem sehr ähnlichen Problem von Ihnen.

Sie können nach Job Shop Scheduling suchen und auch Open Shop Scheduling oder Flow Shop Scheduling können interessante Ausgangspunkte sein

Um einen genetischen Algorithmus zu verwenden, benötigen Sie keine perfekte Lösung. Sie können mit N zufälligen Kandidaten beginnen und auf jeden von ihnen ein Fitnessfunktion anwenden, zum Beispiel:

  • Die Differenz der Nächte, die zwischen dem am meisten beschäftigten Arzt und dem am wenigsten beschäftigten Arzt zugewiesen werden, ist eine Bestrafung der Kostenfunktion
  • Jedes Mal, wenn ein Arzt mehr als 5 Tage pro Woche oder 1 Nacht pro Woche arbeitet, verhängen Sie eine Strafe
  • Jede Ihrer Einschränkungen, etc ...

Wenn Sie N Kandidaten generieren, würden Sie wählen Sie die X besten von ihnen aus , sie wären diejenigen, die die Einschränkungen umso weniger verursachen. Wenn man mit ihnen arbeitet, Kreuzung und Mutation über mehrere Generationen hinweg, kann man eine gute Lösung finden.

Nachdem ich all das besprochen hatte, konnte ich jedes Mal, wenn ich einen genetischen Algorithmus verwendete, der sich mehr auf Mutationen als auf Kreuzungen stützte, ein simuliertes Annealing entwickeln, das mit einer einfacheren Implementierung eine weitaus bessere Leistung erbringt. Die Kosten/Fitness und die Mutationsfunktion für den genetischen Algorithmus werden wahrscheinlich denen eines simulierten Annealing sehr ähnlich sein. Ich würde dort anfangen, siehe @Konrad Morawski Antwort

Google-Suche findet gute Ergebnisse für Job Shop und GA

6
RMalke