通过管道和重定向实现linux管道命令(二)
2012-04-03 15:01
417 查看
标签: 管道 重定向 实现shell命令
分类: 进程间通信
在我的“通过管道和重定向实现linux管道命令”当中实现cat file | sort命令,没有使用标准I/O函数库中提供的popen()函数和pclose()函数,在本文中,我们一起探讨一下通过这两个标准的I/O函数来实现上述这个命令。
先看一下这两个函数的定义吧:
FILE * popen(const char *command, const char *type);
popen()函数用来创建一个管道并启动另外一个进程,新启动的进程要么从该管道当中读出标准输入(输入重定向),要么向该管道写入标准输出(输出重定向)。
具体的第二个参数type表示I/O模式的类型。如果command命令的输出作为其他命令的输入(输出重定向),type为“r”权限;如果command命令的输入为其他命令的输出(输入重定向),type为“w”权限。
int pclose(FILE *stream);
这个函数用来关闭由popen()创建的标准I/O流,等待其中的命令终止,然后返回给shll的终止状态。
在我们对"cat file | sort"程序进行修改之前,先看一个简单的程序:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#define MAXLINE 80
int main()
{
FILE *fp;
char buf[MAXLINE], command[MAXLINE];
int n;
n = fgets(buf, MAXLINE, stdin);
n = strlen(buf);
if(buf[n-1] == '\n') {
n--;
}
/*有关snprintf()函数的是有,具体可查阅printf()函数族的使用*/
snprintf(command, sizeof(command), "head
%s", buf);
fp = popen(command, "r");
while(fgets(buf, MAXLINE, fp) != NULL) {
fputs(buf, stdout);
}
pclose(fp);
return 0;
}
执行结果如下:
^_^[sunny@sunny-laptop ~/summer]47$ ./a.out
file //file是我的输入,下面都是file文件当中的内容
dsf
abcde
92381
8232
sadf
872
1988
2000
1022
2012
^_^[sunny@sunny-laptop ~/summer]48$
程序说明:在调用popen()函数,就是创建了一个新的进程,同时创建了一个管道,注意,type的类型为“r”说明这里是输出重定向,也就是将command的输出作为其他命令的输入,写到创建的管道当中,并不是将其执行的结果输出到标准输出上。下来的话,通过对fp流的读取操作,读取管道当中command的输出结果,为了查
看结果是不是正确的,我们将其显示在了标准输出。
下面实现"cat file | sort"命令:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#define MAXLEN 80
#define MAX 1024
int main()
{
FILE *fpin, *fpout;
char command1[MAXLEN]={0}, command2[MAXLEN]={0}, buff[MAX]={0};
snprintf(command1, sizeof("cat
file"), "cat file");
snprintf(command2, sizeof("sort"), "sort");
fpin = popen(command1, "r"); //输出重定向
fpout = popen(command2, "w"); //输入重定向
while(read(fileno(fpin), buff, MAX) != 0) {
write(fileno(fpout), buff, MAX);
}
/*
*或者这个while循环可以用这个while循环来代替
*
while(fgets(buff, MAX, fpin) != NULL) {
fputs(buff, fpout);
}
*/
pclose(fpin);
pclose(fpout);
return 0;
}
这个程序的执行结果是:
^_^[sunny@sunny-laptop ~/summer]84$ ./a.out
1022
1988
2000
2012
8232
872
92381
abcde
dsf
fan
sadf
^_^[sunny@sunny-laptop ~/summer]85$
程序说明:首先使用snprintf()函数将两个通过管道要执行的命令分别存放在command1和command2当中,然后调用popen函数两次,第一个是所谓的输出重定向,将cat file的结果输入到popen()创建的管道当中,第二个是所谓的输入重定向,将管道当中的数据作为sort命令的输入。之后,通过一个while()循环,读取第一个管道当中的数据到buff变量当中,然后把buff变量当中的数据输入到第二个管道当中,作为sort命令的输入。
小结:在这次实现这个命令的时候,是创建了两个管道,之前的话,只有创建了一个管道就可以实现,但是如果要通过这两个标准的I/O函数来实现的话,我目前没有想到只创建一个管道就来实现的方法。
分类: 进程间通信
在我的“通过管道和重定向实现linux管道命令”当中实现cat file | sort命令,没有使用标准I/O函数库中提供的popen()函数和pclose()函数,在本文中,我们一起探讨一下通过这两个标准的I/O函数来实现上述这个命令。
先看一下这两个函数的定义吧:
FILE * popen(const char *command, const char *type);
popen()函数用来创建一个管道并启动另外一个进程,新启动的进程要么从该管道当中读出标准输入(输入重定向),要么向该管道写入标准输出(输出重定向)。
具体的第二个参数type表示I/O模式的类型。如果command命令的输出作为其他命令的输入(输出重定向),type为“r”权限;如果command命令的输入为其他命令的输出(输入重定向),type为“w”权限。
int pclose(FILE *stream);
这个函数用来关闭由popen()创建的标准I/O流,等待其中的命令终止,然后返回给shll的终止状态。
在我们对"cat file | sort"程序进行修改之前,先看一个简单的程序:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#define MAXLINE 80
int main()
{
FILE *fp;
char buf[MAXLINE], command[MAXLINE];
int n;
n = fgets(buf, MAXLINE, stdin);
n = strlen(buf);
if(buf[n-1] == '\n') {
n--;
}
/*有关snprintf()函数的是有,具体可查阅printf()函数族的使用*/
snprintf(command, sizeof(command), "head
%s", buf);
fp = popen(command, "r");
while(fgets(buf, MAXLINE, fp) != NULL) {
fputs(buf, stdout);
}
pclose(fp);
return 0;
}
执行结果如下:
^_^[sunny@sunny-laptop ~/summer]47$ ./a.out
file //file是我的输入,下面都是file文件当中的内容
dsf
abcde
92381
8232
sadf
872
1988
2000
1022
2012
^_^[sunny@sunny-laptop ~/summer]48$
程序说明:在调用popen()函数,就是创建了一个新的进程,同时创建了一个管道,注意,type的类型为“r”说明这里是输出重定向,也就是将command的输出作为其他命令的输入,写到创建的管道当中,并不是将其执行的结果输出到标准输出上。下来的话,通过对fp流的读取操作,读取管道当中command的输出结果,为了查
看结果是不是正确的,我们将其显示在了标准输出。
下面实现"cat file | sort"命令:
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#define MAXLEN 80
#define MAX 1024
int main()
{
FILE *fpin, *fpout;
char command1[MAXLEN]={0}, command2[MAXLEN]={0}, buff[MAX]={0};
snprintf(command1, sizeof("cat
file"), "cat file");
snprintf(command2, sizeof("sort"), "sort");
fpin = popen(command1, "r"); //输出重定向
fpout = popen(command2, "w"); //输入重定向
while(read(fileno(fpin), buff, MAX) != 0) {
write(fileno(fpout), buff, MAX);
}
/*
*或者这个while循环可以用这个while循环来代替
*
while(fgets(buff, MAX, fpin) != NULL) {
fputs(buff, fpout);
}
*/
pclose(fpin);
pclose(fpout);
return 0;
}
这个程序的执行结果是:
^_^[sunny@sunny-laptop ~/summer]84$ ./a.out
1022
1988
2000
2012
8232
872
92381
abcde
dsf
fan
sadf
^_^[sunny@sunny-laptop ~/summer]85$
程序说明:首先使用snprintf()函数将两个通过管道要执行的命令分别存放在command1和command2当中,然后调用popen函数两次,第一个是所谓的输出重定向,将cat file的结果输入到popen()创建的管道当中,第二个是所谓的输入重定向,将管道当中的数据作为sort命令的输入。之后,通过一个while()循环,读取第一个管道当中的数据到buff变量当中,然后把buff变量当中的数据输入到第二个管道当中,作为sort命令的输入。
小结:在这次实现这个命令的时候,是创建了两个管道,之前的话,只有创建了一个管道就可以实现,但是如果要通过这两个标准的I/O函数来实现的话,我目前没有想到只创建一个管道就来实现的方法。
相关文章推荐
- 通过管道和重定向实现linux管道命令
- 通过管道和重定向实现linux管道命令(二)
- 通过管道和重定向实现linux管道命令
- shell 之 tee 命令,实现重定向到文件的同时仍能 通过管道 (|)传给接下来的命令
- linux学习入门17——LINUX多命令协作、管道及重定向(linuxcast.net)
- Linux基础之IO重定向及管道详解(涉及tr、tee命令)
- Linux多命令协作:管道及重定向
- Linux基本配置和管理 2 ---- Linux多命令协作----管道及重定向
- Linux 变干边学 学习笔记之Linux进程、管道和重定向命令
- Linux下通过ssh-keygen和ssh-copy-id命令实现ssh无密码登录访问
- linux进程间通过管道通信实现简单的tftp
- Linux基础之IO重定向及管道详解(涉及tr、tee命令)
- Linux 重定向、管道和 tr命令总给
- Linux管道和重定向 ---多命令协作
- [Linux] shell read命令 通过管道读取文件 [大三TJB_708]
- Linux命令学习(2)管道和重定向
- linux 的重定向、管道、xargs 命令
- Linux 多命令协作:管道及重定向
- linux 命令之间传递数据的方式:重定向、管道、xargs 命令。
- Linux中>、>>、<、<<重定向及管道命令