在父进程完成打印之前,孩子是否有理由不打印? [英] Is there a reason for the child to not to print until the parent process finishes printing?

查看:53
本文介绍了在父进程完成打印之前,孩子是否有理由不打印?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

#include <stdio.h>
#include <unistd.h>

int do_fork(int depth)
{
    if (!depth) {
        return fork();
    }

    int val = do_fork(depth - 1);

    printf("%d\n", val);

    return val;
}

int main()
{
    int val;
    scanf("%d", &val);
    do_fork(val);
}

我尝试了几次此代码,并在几台不同的机器上使用了几个不同的值.不管数字有多大,我总是看到孩子的pid彼此相邻打印,中间没有零.仅当所有pid都已打印时,子代才开始打印零.

I tried this code several times, with several different values on several different machines. It doesn't matter how big the number is, I always see the pid of the child printed one next to the other with no zeros in between. Only when the pids are all printed, the child starts printing zeros.

此处是一个输入1000的示例.

Here is an example with an input of a 1000.

这种现象是有原因的吗?还是只是随机的?

Is there a reason for this phenomenon or is it just random?

推荐答案

是这种现象的原因吗?还是只是随机的?

Is there a reason for this phenomenon or is it just random?

C和POSIX都没有任何规定可以指导您观察到的特定输出,并且可能会在某些机器上看到不同的结果.特别是,关于父代还是子代首先在 fork()之后使用CPU,不同的操作系统和操作系统版本可能有所不同.(即使在多核系统上,也只有其中一个可以立即成为执行 fork()的内核.)

Neither C nor POSIX has any provisions that direct the particular output you observe, and likely you would see different results on some machines. In particular, different operating systems and operating system versions may differ with respect to whether parent or child first takes the CPU after a fork(). (Even on a multicore system, only one of them can immediately take the core on which fork() was executed.)

但是,派生 do 产生的两个进程在内核中使用相同的打开文件描述进行打印,这意味着将积极地防止它们同时写入该进程.这可能与为什么您看到相同输出的长期运行有关.一个过程将获得一个锁,进行打印,然后释放该锁,并在尝试再次获取该锁后不久.在这种情况下,同一个进程很可能在另一个进程获得另一个锁之前就重新获得了该锁.

However, the two processes resulting from the fork do print using the same open file description in the kernel, and this means that they are actively prevented from writing to it at the same time. This is likely related to why you see long runs of the same output. One process obtains a lock, prints, releases the lock, and very soon after attempts to acquire the lock again. Under these circumstances there is a high probability that the same process reacquires the lock before the other can acquire it.

此外,确实需要一些时间才能在CPU上实际调度新进程.这可能可以解释行为 I 对于输入超过40的程序,即大约35个非零输出,然后在零与非零之间进行相当严格的交替,然后是全零的行为.

Additionally, it does take some time for a new process to actually get scheduled on a CPU. That probably explains the behavior I see for your program for inputs exceeding about 40, which is about 35 nonzero outputs, followed by fairly strict alternation between zero and nonzero, followed by all zeroes.

当然,以上所有假设都完全同时调度了两个进程.如果您只有一个核心同时为这两个核心服务,那么很自然地会得出,每个核心在拥有核心的情况下都会产生自己的输出的长期运行.这很容易表现为两个过程的输出根本没有交织在一起.

Of course, all of the above supposes that the two processes get scheduled concurrently at all. If you have only one core serving both then it naturally follows that each would produce long runs of its own output while it had the core. That could easily manifest as the two processes' outputs not being intermingled at all.

这篇关于在父进程完成打印之前,孩子是否有理由不打印?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆