fork问题的经典理解

main()

    { pid_t pid ;if(pid=fork()<0)

    { printf("error!" );} else { if (pid==0)

    printf("a\n" );else printf ("b\n" );}

    结果是返回a ,b 或者b ,a 因为fork调用将执行两次返回分别从子进程和
父进程返回由于父进程和子进程无关,父进程与子进程都可能先返回

    在看一个程序main()

    { pid_t a_pid ,b_fork;if(a_pid=fork()<0)

    { printf("error!" );} else { if (a_pid==0)

    printf("b\n" );else printf ("a\n" );}

    if(b_pid=fork()<0)

    { printf("error!" );} else { if (b_pid==0)

    printf("c\n" );else printf ("a\n" );}

    如果是创建两个进程则出现结果b c a c a

    事实上,理解fork()的关键在于它的返回点在哪里。fork最特殊的地方就
在于他有两个甚至三个返回值,注意是同时返回两个值。其中pid=0 的这个返回
值用来执行子进程的代码,而大于0 的一个返回值为父进程的代码块。第一次fork
调用的时候生叉分为两个进程,不妨设为a 父进程和b 子进程。他们分别各自在
第二次fork调用之前打印了b 和a 各一次;在第一次叉分的这两个进程中都含有

    if(b_pid=fork()<0)

    { printf("error!" );} else { if (b_pid==0)

    printf("c\n" );else printf ("a\n" );}

    这段代码。很明显,a 父进程和b 子进程在这段代码中又各自独立的被叉分
为两个进程。这两个进程每个进程又都打印了a ,c 各一次。到此,在程序中总
共打印三次a 两次c 和一次b.总共6 个字母。

    注:在第一次叉分为两个进程的时候父子进程含有完全相同的代码(第二次
仍然相同),只是因为在父子进程中返回的PID 的值不同,父进程代码中的PID
的值大于0 ,子进程代码中的值等于0 ,从而通过if这样的分支选择语句来执行
各自的任务。

    我做如下修改

    main()

    { pid_t pid ;if(pid=fork()<0)

    { printf("error!" );} else { if (pid==0)

    printf("a\n" );else printf ("b\n" );} 结果是返回a ,b 或者b ,
a 因为fork调用将执行两次返回分别从子进程和父进程返回由于父进程和子进程
无关,父进程与子进程都可能先返回

    在看一个程序

    main()

    { pid_t a_pid ,b_fork;if(a_pid=fork()<0)

    { printf("error!" );} else { if (a_pid==0)

    printf("b\n" );else printf ("a\n" );}

    if(b_pid=fork()<0)

    { printf("error!" );} else { if (b_pid==0)

    printf("c\n" );else printf ("a\n" );}

    如果是创建两个进程则出现结果b c a c a

   

事实上,理解fork()的关键在于它的返回点在哪里。fork最特殊的地方就
在于他有两个甚至三个返回值,注意是同时返回两个值。其中pid=0 的这个返回
值用来执行子进程的代码,而大于0 的一个返回值为父进程的代码块。第一次fork
调用的时候生叉分为两个进程,不妨设为a 父进程和b 子进程。他们分别各自在
第二次fork调用之前打印了b 和a 各一次;在第一次叉分的这两个进程中都含有
if(b_pid=fork()<0)

    { printf("error!" );} else { if (b_pid==0)

    printf("c\n" );else printf ("a\n" );} 这段代码。很明显,a 父
进程和b 子进程在这段代码中又各自独立的被叉分为两个进程。这两个进程每个
进程又都打印了a ,c 各一次。到此,在程序中总共打印三次a 两次c 和一次b.
总共6 个字母。

    注:在第一次叉分为两个进程的时候父子进程含有完全相同的代码(第二次
仍然相同),只是因为在父子进程中返回的PID 的值不同,父进程代码中的PID
的值大于0 ,子进程代码中的值等于0 ,从而通过if这样的分支选择语句来执行
各自的任务。

    我做如下修改

    #include ;#include ;

    main()

    { pid_t pid ;printf("fork !" ); // printf("fork !n");

    pid=fork();

    if(pid < 0 )

    printf("error in fork!" );else if (pid == 0)

    printf("i am the child process , my process id is %dn",getpid
());else printf ("i am the parent process, my process id is %dn",
getpid());}

    结果是[root@localhost c]# ./a.out fork!i am the child process, my
process id is 4286 fork !i am the parent process , my process id is
4285

    但我改成printf("fork !n");后,结果是[root@localhost c]# ./a.out
fork!

    i am the child process, my process id is 4286 i am the parent process,
my process id is 4285

    为什么只有一个fork!打印出来了?上一个为什么有2 个?

    printf("AAAAAAAA");//print 一次;这里会print 2 次如果你将 printf
("AAAAAA")换成 printf ("AAAAAAn" )那么就是只打印一次了。

    主要的区别是因为有了一个 n回车符号这就跟Printf的缓冲机制有关了,printf
某些内容时,操作系统仅仅是把该内容放到了stdout的缓冲队列里了,并没有实
际的写到屏幕上但是,只要看到有 n则会立即刷新stdout,因此就马上能够打印
了。

    运行了printf("AAAAAA")后, AAAAAA 仅仅被放到了缓冲里,再运行到fork
时,缓冲里面的 AAAAAA 被子进程继承了因此在子进程度stdout缓冲里面就也有
了 AAAAAA.所以,你最终看到的会是 AAAAAA 被printf了2 次!!!!

    而运行 printf ("AAAAAAn" )后, AAAAAA 被立即打印到了屏幕上,之后
fork到的子进程里的stdout缓冲里不会有 AAAAAA 内容因此你看到的结果会是 AAAAAA
被printf了1 次!!!!

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值