2016-06-30 11 views
0

Ich habe ein Skript (Python), das Subprozess verwendet, um ein anderes Skript aufzurufen. Das übergeordnete Skript schreibt gleichzeitig in die Konsole und eine Protokolldatei (ich habe den Code aus der akzeptierten Antwort auf this question verwendet, um die Ausgabe zu teilen), aber die Druckanweisungen für untergeordnete Prozesse werden nur in die Standardausgabe und nicht in die Protokolldatei geschrieben.Schreiben in eine Datei aus einem Subprozess und Elternprozess gleichzeitig

Ich weiß, warum das ist: Der Subprozess hat Stdout auf normale Stdout gesetzt, nicht die spezielle Tee-Objekt, dass der Elternprozess hat. Ich habe versucht, das Tee-Objekt als Argument für den Subprozess zu übergeben, aber ich habe gelernt, dass man Objekte nicht als Argumente an Subprozesse übergeben kann. Mein Backup-Plan bestand darin, die Pfadzeichenfolge für die Datei, in die geschrieben werden soll, zu übergeben und dann den Subprozess zu veranlassen, ein eigenes Abschlagobjekt mit der gleichen Datei zu erstellen.

Meine Frage ist, wenn beide Prozesse zur gleichen Zeit in die gleiche Datei schreiben, wird die Ausgabe durcheinander gebracht? Ich benutze open ("file", "w") im übergeordneten Prozess, und dies wird zuerst aufgerufen, und ich verwende open ("file", "a") im untergeordneten Prozess. Hypothetisch sollte die Datei die Ausgabe der Druckanweisungen in der richtigen Reihenfolge enthalten, da das Anhängen an eine Datei mit "a" bedeutet, dass die Zeilen immer zum aktuellen Ende der Datei hinzugefügt werden, oder nicht? Oder gibt es Regeln zum Öffnen einer Datei, die verhindern, dass sie gleichzeitig von zwei Prozessen geöffnet wird?

POST_TEST: Nach ein paar Tests selbst zu tun, fand ich folgendes: -Sie sind erlaubt zu öffnen („Datei“, ‚w‘) mehrmals in einer Reihe -Sie öffnen dürfen („Datei“, 'w') und dann öffnen ("file", "a") - Im ersten Fall überschreibt der Kindprozess die Datei vollständig. - Im zweiten Fall ist die Reihenfolge nicht korrekt und einige Ausgaben scheinen verloren zu sein.

Meine neue Frage ist dann, welche alternative Lösung sollte ich verwenden, um in eine Datei aus dem Eltern- und Kind-Prozess zur gleichen Zeit zu schreiben, ohne Zeilen nicht in der Reihenfolge oder Überschneidungen zu bekommen?

+0

Google "Mutex". Ein Mutex ist eine MUTUAL EXKLUSIVE Sperre für eine Ressource, die Kollisionen vermeidet, wenn zwei Prozesse dieselbe Ressource verwenden. –

+0

http://stackoverflow.com/questions/489861/locking-a-file-in-python –

+1

Der Prozess, der im 'a'-Modus geöffnet wird, schreibt immer am Ende der Datei. Aber derjenige, der in "w" Modus öffnet, wird nicht. Sie müssen beide im "a" -Modus öffnen. – Barmar

Antwort

0

Vielen Dank Bamar für die Vorschläge: mit 'a' für die erste und zweite open() funktioniert. Wenn Sie dies für eine Datei tun müssen, die bereits existiert, können Sie file.truncate() verwenden, um die Datei zu leeren, bevor Sie sie anhängen.

+0

Es ist nicht garantiert, dass alle Schreibvorgänge auf allen Systemen am Ende sind, wenn die Datei im "a" -Modus geöffnet wird. Es ist nicht garantiert, dass große 'write()' s atomar sind (die Ausgabe von mehreren Prozessen kann verschachteln). – jfs

0

Beim Öffnen einer Datei im 'w'-Modus wird die Datei abgeschnitten (as documented). Das Öffnen einer Datei im 'a'-Modus funktioniert möglicherweise unter einigen-Systemen. POSIX says for O_APPEND flag:

Wenn gesetzt, sollte der Dateioffset vor jedem Schreibvorgang auf das Ende der Datei gesetzt werden.

write()s that are larger than PIPE_BUF may interleave:

POSIX.1-2008 nicht sagen, ob Schreibanforderungen für mehr als {PIPE_BUF} Bytes atomar sind, erfordert aber, dass Schreiben von {PIPE_BUF} oder weniger Bytes Atom sein soll.


Q: welche alternative Lösung soll ich in eine Datei aus zu schreiben, verwende sowohl für die Eltern-Kind-Prozess zur gleichen Zeit, ohne Linien in der falschen Reihenfolge oder überlappend zu bekommen?

Öffnen die Dateien mit Zeilenpuffermodus (1), den internen Puffer am Ende jeder Zeile zu spülen, - es sollte die ungefähre relative Reihenfolge der Leitungen erhalten. Wenn Zeilen weniger als PIPE_BUF (4096 Bytes auf meinem System) sind, sollten sie sich nicht "überlappen".


Die subprocess kann Daten an die Standardausgabe und Ihren Prozess Mutter Python schreiben sie in eine Datei schreiben Sie können in beliebiger Reihenfolge. Siehe how teed_call() function is implemented.

+0

Ich habe nichts gegen den Downvote, aber ich würde eine Erklärung schätzen, die es erlauben würde, die Antwort besser zu machen. – jfs

+0

Ich hasse es, wenn Leute ablehnen, ohne zu sagen, warum sie es tun –

Verwandte Themen