コマンドを並行して実行するスクリプトを作成しました。私は彼ら全員に同じログファイルにエントリを書き込ませました。順序が間違っていても、エントリがインターリーブされていても問題ありませんが、一部のエントリが欠落していることに気付きました。おそらく、書き込む前にファイルをロックする必要がありますが、複数のプロセスが同時にファイルに書き込もうとすると、エントリが失われるというのは本当ですか?
2 に答える
はい。異なるプロセスが個別に開いて同じファイルに書き込むと、書き込みが重複したり、データが失われたりする可能性があります。これは、各プロセスが独自のファイルポインターを取得し、ローカル書き込みによってのみ進行するために発生します。
ロックする代わりに、すべてのワーカープロセスの祖先でログファイルを一度開いて、それを継承しfork()
、ログに使用することをお勧めします。これは、いずれかのプロセスが新しいエントリを書き込むときに進む単一の共有ファイルポインタがあることを意味します。
スクリプトでは、「>> file」(2倍大きい)を使用して、そのファイルに出力を追加する必要があります。インタプリタは宛先を「追加」モードで開きます。プログラムも追加したい場合は、以下の指示に従ってください。
「追加」モード(「a +」)でテキストファイルを開き、全行のみを印刷することを優先します(複数の「印刷」の後に最後の「println」を実行しないでください。ただし、単一の「println」で行全体を印刷してください。 )。
fopenのドキュメントには次のように記載されています。
DESCRIPTION
The fopen() function opens the file whose pathname is the
string pointed to by filename, and associates a stream with
it.
The argument mode points to a string beginning with one of
the following sequences:
r or rb Open file for reading.
w or wb Truncate to zero length or create file
for writing.
a or ab Append; open or create file for writing
at end-of-file.
r+ or rb+ or r+b Open file for update (reading and writ-
ing).
w+ or wb+ or w+b Truncate to zero length or create file
for update.
a+ or ab+ or a+b Append; open or create file for update,
writing at end-of-file.
文字bは効果がありませんが、ISO C標準への適合が許可されています(standards(5)を参照)。読み取りモード(mode引数の最初の文字としてr)でファイルを開くと、ファイルが存在しないか、読み取ることができない場合は失敗します。
追加モード(mode引数の最初の文字としてa)を使用してファイルを開くと、fseek(3C)の呼び出しに関係なく、ファイルへの後続のすべての書き込みがその時点で現在のファイルの終わりに強制されます。2つの別々のプロセスが追加のために同じファイルを開く場合、各プロセスは、他のプロセスによって書き込まれている出力を破壊することを恐れることなく、ファイルに自由に書き込むことができます。 2つのプロセスからの出力は、書き込まれた順序でファイルに混在します。
'println'(または同等のもの)のみを使用することを優先したいのは、この混合のためです。