织梦CMS - 轻松建站从此开始!

罗索

管道应用实例

落鹤生 发布于 2011-05-13 09:58 点击:次 
使用管道的C程序实例:父子进程间建了两个管道,用于相互读写对方的信息。
TAG:

管道具有以下特点:

(1)半双工数据只能在一个方向上流动。

(2)只能在具有公共祖先的进程间使用通常,一个管道由一个进程创建,然后该进程调用fork,此后父子进程间就可应用该管道。

(3)单独构成一种独立的文件系统。管道对于管道两端的进程而言就是一个文件,但它不是变通的文件,而是单独构成一种文件系统,并且只存在于内存中。

(4)数据从管道的一端写入,但从另一端读出。一个进程向管道中写的内容被管道另一端的进程读出。写入的内容每次都添加在管道缓冲区的末尾,并且每次都是从缓冲区的头部读出。

(5)没有名字

(6)管道的缓冲区是有限的(管道存在于内存中,在管道创建时,为缓冲区分配一个页面大小)。

(7)管道传送的数据是无格式的

(8)写入管道的数据读完后就从管道中消失

 

管道的创建和读写

一个进程在由pipe()创建管道后,一般再fork一个子进程,然后通过管道实现父子进程间的通信。

#include <unistd.h>
int pipe(int fd[2])

管道两端可分别用描述字fd[0]和fd[1]来描述,一端只能用于读,由描述字fd[0]表示(管道读端);另一端则只能用于写,由描述字fd[1]来表示(管道写端)。

 

 

使用管道的C程序实例:父子进程间建了两个管道,用于相互读写对方的信息。

#include <unistd.h>
#include <sys/types.h>

int main(void)
{
        int pipe1_fd[2], pipe2_fd[2];
        char * parent_talks[] = {"Hi, my baby",
                                 "Can you tell daddy date and time?",
                                 "Daddy have to leave here, bye!",
                                 NULL
                                };

        char * child_talks[] = {"Hi, daddy",
                                "Sure,",
                                "Bye!",
                                NULL
                               };

        char parent_buf[256], child_buf[256];
        char * parent_ptr, * child_ptr;
        int i,j, len;
        int child_status;
        time_t curtime;

        if(pipe(pipe1_fd)<0)
        {
                printf("pipe1 create error\n");
                return -1;
        }

        if(pipe(pipe2_fd)<0)
        {
                printf("pipe2 create error\n");
                return -1;
        }

        if(fork()==0)   //child
        {
                printf("\n");

                //pipe1_fd[0] is used to read, pipe2_fd[1] is used to write
                close(pipe1_fd[1]);
                close(pipe2_fd[0]);

                i = 0;
                child_ptr = child_talks[i];
                while(child_ptr != NULL)
                {
                        len = read(pipe1_fd[0], child_buf, 255);
                        child_buf[len] = '\0';
                        printf("Parent: %s\n", child_buf);

                        if (i == 1) {
                                time(&curtime);
                                len = sprintf(child_buf, "%s %s", child_ptr, ctime(&curtime));
                                child_buf[len-1] = '\0';
                                write(pipe2_fd[1], child_buf, strlen(child_buf));
                        }
                        else {
                                write(pipe2_fd[1], child_ptr, strlen(child_ptr));
                        }

                        child_ptr = child_talks[++i];
                }
                close(pipe1_fd[0]);
                close(pipe2_fd[1]);
                exit(0);
        }
        else { //parent

                //pipe1_fd[1] is used to write, pipe2_fd[0] is used to read
                close(pipe1_fd[0]);
                close(pipe2_fd[1]);

                j = 0;
                parent_ptr = parent_talks[j];
                while (parent_ptr != NULL) {
                        write(pipe1_fd[1],parent_ptr,strlen(parent_ptr));

                        len = read(pipe2_fd[0],parent_buf,255);
                        parent_buf[len] = '\0';
                        printf("Child: %s\n", parent_buf);

                        parent_ptr = parent_talks[++j];
                }

     close(pipe1_fd[1]);
     close(pipe2_fd[0]);
     wait(&child_status);
     exit(0);
        }
}

管道函数

#include <stdio.h>
FILE *popen(const char *cmdstring, const char *type);
int pclose(FILE *fp);

用于计算简单的数学表达式的shell脚本calculator

#filename: calculator
#!/bin/sh

while :
do
read expression
expression=`echo "$expression" | sed 's/\*/\\\*/'`
if [ "$expression" = "" ] ; then
        exit
fi
eval "expr $expression"
done

下面的程序使用popen来执行calculator脚本:先接收用户输入的表达式,然后通过popen打开的文件句柄传送给该脚本,脚本将执行该表达式并把结果输出到标准输出。输入quit退出程序。

#include <stdio.h>
#include <string.h>

int main(void)
{
        char buf[256];
        FILE * fp = popen("./calculator", "w");
        if ( fp == NULL) {
                printf("Fail to poen ./calculator...\n");
                exit(-1);
        }
        while (1) {
                printf("Enter a expression: ");
                fgets(buf, 256, stdin);
                if (strncmp("quit", buf, 4) == 0) {
                        fprintf(fp, "\n");
                        fflush(fp);
                        pclose(fp);
                        exit(0);
                }
                fprintf(fp, "%s", buf);
                fflush(fp);
                sleep(1);
        }

}

注:输入表达式时,运算符两端要有空格

(studyarea)
本站文章除注明转载外,均为本站原创或编译欢迎任何形式的转载,但请务必注明出处,尊重他人劳动,同学习共成长。转载请注明:文章转载自:罗索实验室 [http://www.rosoo.net/a/201105/11672.html]
本文出处:百度博客 作者:studyarea
顶一下
(0)
0%
踩一下
(0)
0%
------分隔线----------------------------
发表评论
请自觉遵守互联网相关的政策法规,严禁发布色情、暴力、反动的言论。
评价:
表情:
用户名: 验证码:点击我更换图片
栏目列表
将本文分享到微信
织梦二维码生成器
推荐内容