それが私のコードです。
#include <stdio.h>
#include <stdlib.h>
int main ( int argc, char *argv[] )
{
int i, pid;
for(i = 0; i < atoi(argv[1]); i++) {
pid = fork();
if(pid < 0) {
printf("Error");
exit(1);
} else if (pid == 0) {
printf("Child (%d): %d\n", i + 1, getpid());
exit(0);
} else {
wait(NULL);
}
}
}
出力はそのようなものです。
Child (1): 5676
Child (2): 4624
Child (3): 4800
Child (4): 5596
Child (5): 5580
しかし、それは私の宿題で期待される出力ではありません。そうあるべきです。コードの何が問題になっていますか?誰かが私を助けることができますか?
Child (2): 4625
Child (1): 4624
Child (3): 4626
Child (4): 4627
Child (5): 4628
ご協力ありがとうございました。今から試してみます。
P.S.すみません、私の英語は下手です。私の言ったことをご理解いただければ幸いです。
あなたのコードは私のコンピューターで完全に機能します。 OSに依存する可能性があります。
ただし、プログラムに引数が指定されていない場合のセグメンテーション違反を回避するために、argcが1に等しくないかどうかを確認する必要があります。
システムは、プロセスに割り当てるために無料のPIDを取ります。プロセスIDを4000にフォークし、子IDを3900にすることができます。最初のプロセスIDは決して同じではないため、宿題の紙に数字を入れてはいけません。
順序付けられていない出力が得られる理由は、どの子がいつアクティブになるかを正確に予測できないためです。そのため、2番目の子がfork()
されて開始されるまで、最初の子の実行が遅れる場合があります。
これはOSに依存しますが、通常、子供はシーケンシャルPIDを取得します。
どちらの問題も、スケジュールされたタスクで問題になることはありません-絶対PIDは実際には重要ではありません(前述のように、すべてのOSは独自の処理を実行でき、PIDを順番にまたはランダムに割り当てます)。 :子の各部分の実行時間が異なる可能性があるため、出力が順序付けられません。これは、データが正しく転送されている限りカウントされます。これは、親がシーケンスを生成してからフォークする場合です。この場合、子プロセスのメモリレイアウトは、フォーク時の親プロセスのメモリレイアウトと同じです。したがって、親は、すでに実行中の子に影響を与えることなく、その「データ転送配列」を変更できます。
混乱を減らすために、すべての行のPIDの出力を削除することができます。子プロセスのそれぞれの開始時に出力できるかもしれませんが、その後は、たとえば次のように言うだけで十分です。 Child 3: straight length 6 <S6,H5,C4,S3,H2,SA>
PIDを繰り返さずに。
その期待される出力で、ほとんどの場合、宿題は最初にすべてのプロセスをフォークしてから、waitを呼び出す必要があります。
ループ内の待機呼び出しをスキップし、wait
が-1
を返しerrno
がECHILD
に設定されるまでループする別の呼び出しを実行します。子の出力順序はランダムであるか、少なくとも完全な順序ではないため、必ずしも2 1 3 45である必要はないことに注意してください。
これは単なる推測ですが、より具体的な回答が必要な場合は、より多くの情報を提供する必要があります。