Zuerst hoffe ich, dass Sie eine Transaktion verwenden. Andernfalls kann es eine Wettlaufsituation zwischen 1 und 2 geben.
Ich denke, Ihre Frage ist "Woher weiß Ihr Programm, wenn mehr Informationen in einer SQL-Tabelle verarbeitet werden?" Es gibt mehrere Möglichkeiten, dies zu tun.
Die einfachste ist . Ihr Programm prüft nur gelegentlich, ob es Arbeit gibt. Wenn nicht, schläft es eine Weile. Wenn die Überprüfung billig ist oder Sie nicht sehr oft überprüfen müssen, ist die Abstimmung in Ordnung. Es ist ziemlich robust, es gibt keine Koordination zwischen dem Arbeiter und dem Lieferanten. Der Arbeiter sucht nur nach Arbeit.
Eine andere Möglichkeit besteht darin, das Programm auf eine Art von I/O zu blockieren, wie auf das Sperren einer Datei zu warten. Darum geht es bei Semaphoren. Es geht so.
- Die Warteschlange ist leer.
- Der Produzent erhält eine exklusive Sperre für die Semaphor-Datei.
- Ihr Arbeiter versucht, die Semaphor-Datei zu sperren, sie blockiert.
- Der Produzent fügt der Warteschlange hinzu und gibt seine Sperre frei.
- Der Arbeiter entsperrt sofort.
- Überprüft die Warteschlange
- Funktioniert.
... aber das Zurücksetzen des Systems ist ein Problem. Der Produzent weiß nicht, wann die Warteschlange wieder leer ist, ohne zu pollen.Und dies erfordert, dass alles, was der SQL-Tabelle hinzugefügt wird, über diese Prozedur informiert ist und sich auf demselben Computer befindet. Selbst wenn es funktioniert, ist es sehr anfällig für Deadlocks und Race Conditions.
Ein anderer Weg ist über Signale. Der Erzeugerprozess sendet ein Signal an den Arbeiterprozess, um zu sagen "Ich habe etwas Arbeit hinzugefügt". Wie oben erfordert dies eine Koordination zwischen den Dingen, die zu der SQL-Tabelle und den Arbeitern hinzugefügt werden.
Eine bessere Lösung besteht darin, SQL nicht für eine Arbeitswarteschlange zu verwenden. Es ist von Natur aus etwas, was Sie abfragen müssen. Verwenden Sie stattdessen eine Named- oder eine Netzwerk-Pipe. Pipes fungieren automatisch als Warteschlange. Produzenten schreiben an das Rohr, wenn sie Arbeit hinzufügen. Der Arbeiter verbindet sich mit dem Rohr und liest daraus, um mehr Arbeit zu bekommen. Wenn es keine Arbeit gibt, blockiert es ruhig das Warten auf Arbeit. Die Pipe kann alle Informationen enthalten, die für die Arbeit erforderlich sind, oder sie kann nur einen Hinweis darauf enthalten, dass an einem anderen Ort gearbeitet wird (z. B. eine ID für eine Zeile).
Schließlich, je nachdem, wie viel Verarbeitung durchgeführt werden muss, könnten Sie versuchen, alle diese Verarbeitung in einer gespeicherten Prozedur, ausgelöst durch eine Tabellenaktualisierung, durchzuführen.
Semaphore sind für Multithreading-Synchronisation. Ich kann mir nicht vorstellen, dass sie hier nützlich wären. – Riley
Dies ist ein Beispiel für das "Producer/Consumer Problem". Semaphore (und andere Synchronisationsgrundelemente) sind nur dann anwendbar, wenn Sie sowohl den Producer (den externen Prozess) als auch Ihren Consumer (Ihr Programm) ändern können, um diese zu nutzen. Sie werden Ihnen in einer Singlethread-Anwendung nicht helfen oder wenn der Hersteller keine systemweite IPC nutzen kann (oder kann). Die Verwendung von sleep ist akzeptabel, obwohl Sie einen Systemzeitgeber verwenden sollten, um den Kernel freizugeben. – Dai
Ich bin mir nicht sicher, was Sie fragen. Sie möchten nicht, dass das Programm beendet wird. Beenden Sie das Programm nicht am Ende der Schleife. Ich denke, deine eigentliche Frage ist: "Wie kann ich mein Programm am besten warten lassen, bis es noch mehr Sachen zu verarbeiten gibt?" – Schwern