Job-Scheduling-Problem

stimmen
8

Ich arbeite an einer Anwendung, wo ich brauche Arbeitsplätze für die Mitglieder auf einem rotierenden Zeitplan automatisch zu planen. Ich bin nicht sehr gut an Regeln zu erklären, so dass hier einige Daten, um zu helfen:

Position: Ein Jobtitel, mit Regeln wie montags und mittwochs wöchentlich.
Kategorien: Eine Reihe von Positionen
Gruppen: Eine weitere Reihe von Positionen. Positionen in der gleichen Gruppe können nicht auf den gleichen Tag zugeordnet werden
Mitglieder: Benutzer der Positionen zu einem bestimmten Zeitpunkt zugewiesen.

Für jeden Tag im Monat werden die Mitglieder an Positionen zugewiesen (beide in aufsteigender Reihenfolge). Wenn ein Mitglied in eine Position in einer Kategorie zugeordnet ist, kommt das nächste Mal eine Position, in der gleichen Kategorie auf, das nächste Mitglied in alphabetischer Reihenfolge (oder der Anfang der Liste) wird zugewiesen zB.

Mitglieder: M1, M2, M3, M4
Positionen in Kategorie C1: P1, P2, P3
Mitglieder in Position P1: M1, M2, M3, M4
Mitglieder in Position P2: M1, M2, M3
Mitglieder in Position P2: M1, M3, M4

Wenn M1 für P1 zugewiesen, wenn P2 als nächstes kommt, wird M2 zugeordnet werden. Eine zusätzliche Schicht von Komplexität eingeführt wird, wo, wenn P3 nächste Stelle kommt, wird M3 zugeordnet. Das System des Überblick über die Tatsache zu halten hat, dass M2 wurde ‚übersprungen‘ und weist M2 nächste falls vorhanden, dann M4 nächstes zuweisen, oder warten, bis es wird zu einer Position, wo M2 verfügbar ist (dies wird zusätzlich komplex, wenn es viele ‚übersprungen 'Mitglieder).

Ein Mitglied wird auch übersprungen werden, wenn er angezeigt hat er nicht zu diesem Zeitpunkt zur Verfügung stehen wird. Das System muss Priorität auf übersprungenen Mitgliedern platzieren, sie irgendwie zu identifizieren, wenn sie kommen und dann in der Liste auf die nächste logische Person zu springen. Skipping gilt auch wegen Datum Auseinandersetzungen zu Gruppen.

Ich habe bereits eine temporäre [und chaotisch] Lösung, die ich nicht mehr verstehen, obwohl ich eine Menge Kommentare in ihm jeden Schritt erklären. Seine Schwächen sind mit den übersprungenen Mitgliedern im Umgang.

Wenn Sie codieren würden diese wie würden Sie vorgehen? Ich bin die Umsetzung dieses in PHP aber Pseudo-Code würde auch funktionieren.

Veröffentlicht am 19/12/2009 um 11:20
quelle vom benutzer
In anderen Sprachen...                            


3 antworten

stimmen
1

uff. Ich verstehe Sie nicht Beschreibung, aber in ähnlichen Situationen habe ich verwendet, SQL, diese Art von Problem zu lösen. Wenn Sie PHP verwenden, ich denke, Sie haben SQL zur Verfügung.

was ich würde vorschlagen, ist zu tun, einen Weg zu finden, diese Informationen in eine Reihe von Tabellen zu speichern und dann arbeiten Sie heraus, was SQL-Abfrage gibt Ihnen die Antwort, die Sie wollen. es ist ziemlich oft viel einfacher in SQL zu tun, als es in einer prozeduralen Sprache ist.

für den übersprungenen Teil, zum Beispiel, haben Sie vielleicht eine Spalte haben, das, wenn jemand aufzeichnet wurde zuletzt zugewiesen, und dann, um damit (so dass Sie wählen Sie die Person, die für eine lange Zeit zugewiesen wird nicht). alternativ könnte man die Anzahl der als Säule und um damit übersprungen.

Beantwortet am 19/12/2009 um 13:09
quelle vom benutzer

stimmen
6

Meine Lösung: Sie benötigen eine Priorityqueue (die in PHP unter SplPriorityQueue verfügbar ist). Die Priorityqueue gibt Ihnen Elemente mit absteigender Priorität (sortiert nach Werten, der kleinste Wert hat die höchste Priorität).

Jedes Mitglied erhält einen zugewiesenen Wert. Dieser Wert ist eine ASCII-Zahl mit n Ziffern (Sie 8 Ziffern für die Bequemlichkeit verwenden könnten), mit Nullen bis n Positionen gefüllt. Danach anhängen Sie den Namen ein. Sie fügen auch die verfügbaren Positionen für jedes Mitglied

So (n = 5):

  • M1-Wert: 99999Albert P1, P2, P3
  • M2-Wert: 99999Susi P1, P2
  • M3-Wert: 99999Bob P1, P3

Dies macht es einfach Mitglieder nach Priorität und Namen zu sortieren.

Vorbereitung:

Ein sonniger Tag. Sie sind das Abrufen der zugewiesenen Positionen und eine Kategorie für einen bestimmten Tag. Jedes Mitglied ist auf einer langen Liste geladen. Jedes Mitglied, das zeigt nach oben nicht auf der Arbeit ist nicht geladen, aber sein Wert wird von minus zwei verringert. Bob ist nicht hier, also sein neuer Wert bekommt 99997Bob. Das bedeutet, dass Bob automatisch das nächste Mal ausgewählt wird. Alle anderen Mitglieder erhalten ihren Wert durch minus eins verringert.

Die Positionen für einen bestimmten Tag zugeordnet sind (Verwendung SplObjectStorage) abgebildet:

P1-> M1, M2, M3, M4 usw. P2-> usw.

Die Karte enthält nur die Positionen, die an diesem Tag zugewiesen werden müssen. Nach dem

Filter: Sie müssen die Gruppen suchen und alle Positionen auf der Karte löschen, die nicht an diesem Tag zugeordnet werden können. Ihre Beschreibung der Gruppe ist ein wenig unklar.

Zuordnen:

  • Sie wählen die Position zuweisen
  • Holen Liste der Mitglieder, die die Position füllen
  • Entfernen verfügbare Mitglieder aus der Liste und legt sie in die Priorityqueue
  • Vergeben die Position durch extract () von Priorityqueue (korrekte Zuordnung automaticially done). Jedes Mitglied, das Willen zugewiesen bekommt seinen Wert um eins erhöht (also die Abnahme und Zunahme Ebenen, wenn Sie hier sind und arbeiten). Wenn Sie auch hier und nicht in eine Position aus irgendeinem Grund zugewiesen sind, erhalten Sie eine kleine Strafe von einem. Wenn Sie hier nicht, erhalten Sie eine Strafe von zwei Kindern.
  • setzen übrige Mitglieder auf der Liste nach Fertigstellung wieder, deaktivieren Sie das PQueue und fahren Sie mit dem nächsten Einsatz.

Vorsichtsmaßnahmen:

  • Sie müssen vorsichtig sein, dass immer genügend Leute für eine Position.
Beantwortet am 02/01/2010 um 16:10
quelle vom benutzer

stimmen
0

Was ich verstehe, ist es ‚m‘ Mitglieder und ‚n‘ Positionen.

Kategorie: eine Gruppe von Positionen - ein Mitglied, das eine Position in der Kategorie zugeordnet ist, eine andere nicht haben?

Gruppen: eine Gruppe von Positionen - Positionen in der gleichen Gruppe muss an verschiedenen Tagen zugeordnet werden.

Letzte Sache, hat eine Position, eine Liste der Mitglieder, die es füllen.

Betrachtet man dies aus einer Datenstruktur Sicht der Mitglieder in einer verknüpften Liste setzen - jedes Mitglied hat eine zusätzliche Liste von [Position, Tag] haben, dass sie endlich zugeordnet sind. Dann wird für jede Position, haben eine Liste von Verweisen auf die Elemente, die diese Position ausfüllen kann. Implementieren Kategorien als eine andere Liste von Referenzen für eine Position als auf welche Kategorien es in ist.

Die eigentliche Aufgabe: einen Tageszähler = 0, und durch die Positionen durchlaufen. Für jede Position P, durchlaufen die Mitglieder, die es füllen. Ein Mitglied M kann die Position ausfüllen, wenn:

  • Jede Position, die er gefüllt hat P2 keine Kategorie mit P. teilen
  • Jede Position, die er P2 mit Tag gefüllt = Tageszähler keine Gruppe mit P. teilen

Wenn er die Position ausfüllen kann, wird die [Position, Tag] Paar an das Element hinzugefügt, und das Knotens Elements ist an das Ende der Liste verschoben (aus diesem Grunde Referenzen sind notwendig - alle Referenzen noch gültig sind, auch wenn die Knoten verschoben). Dadurch wird sichergestellt, dass die ‚übersprungen‘ Mitglieder gegeben höchste Priorität, und die Mitglieder, die nicht erreicht wurden nächsthöhere Priorität.

Sobald eine Position gefüllt ist, in die nächste Position gehen. Wenn die Position einer Gruppe mit einer Position bereits belegt teilt, es überspringen, Iterieren durch alle Positionen, bis Sie so viele Positionen zuweisen können, wie Sie 1. Dann, am Tag können, den Tageszähler erhöhen und wiederholen Sie für Tag 2. Dies sollte Ihnen eine maximale Belegung (nicht über maximal sicher) für alle Arbeitsplätze.

Tipp: Wenn Sie ein Mitglied bis zum Ende der Mitgliederliste zu bewegen, mit zu verhindern, um die Liste zu durchqueren, einen Verweis auf das Ende halten - für die nächste Position, müssen Sie von dem ohnehin Anfang beginnen, so dass es kein Sinn, geht durch das ganze Ding.

Beantwortet am 02/01/2010 um 18:16
quelle vom benutzer

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more