教程集 www.jiaochengji.com
教程集 >  脚本编程  >  shell  >  正文 玩转Linux文件描述符和重定向

玩转Linux文件描述符和重定向

发布时间:2014-12-08   编辑:jiaochengji.com
本文介绍linux中文件描述符与重定向的相关知识,文件描述符是与文件输入、输出相关联的整数,它们用来跟踪已打开的文件。有需要的朋友参考下。

linux下的文件描述符是与文件输入、输出相关联的整数。它们用来跟踪已打开的文件。
最常见的文件描述符是stdin、stdout和stderr.我们可以将某个文件描述符的内容重定向到另一个文件描述符中。

下面给出一些对文件描述符进行操作和重定向的例子。

1.5.1 预备知识
我们在编写脚本时会频繁使用标准输入(stdin)、标准输出(stdout)和标准错误(stderr)。

通过内容过滤将输出重定向到文件是我们从事的基础任务之一。

当命令输出文本时,这些输出文本有可能是错误信息,也可能是正常的(非错误的)输出信息。
单靠查看输出的文本本身,  我们无法区分哪些是正常的输出文本,哪些是错误文本。不过,我们可以通过文件描述符来解决这个问题,将那些与特定描述符关联的文本提取出来。
文件描述符是与一个打开的文件或数据流相关联的整数。文件描述符0、1以及2是系统预留的。
0——stdin(标准输入)
1——stdout(标准输出)
2——stderr(标准错误)

1.5.2  实战演练
将输出文本重定向或保存到一个文件中:
 

复制代码 代码示例:
$echo"This is a sample text 1">temp.txt
 

这种方法通过截取文件的方式,将输出文本存储到文件temp.txt中,也就是说在把echo命令的输出写入文件之前,temp.txt中的内容首先会被清空。
接下来,再看另一个例子:
 

复制代码 代码示例:
$echo "this is sample text 2" >>temp.txt
 

这种方法会将文本追加到目标文件中。
>和>>并不相同。尽管这两个操作符都可以将文本重定向到文件,但是前者会先清空文件,再写入内容;而后者会将内容追加到现有文件的尾部。
可以用下面的方法查看文件内容:
 

复制代码 代码示例:
$cat temp.txt
this is sample text 1
this is sample text 2
 

在linux操作系统中,当使用重定向操作符时,重定向的内容不会出现在终端,而是直接被导入文件。重定向操作符默认使用标准输出。如果想使用特定的文件描述符,你必须将描述符置于操作符之前。

>等同于1>;对于>>来说,情况也类似(即>>等同于1>>)。
来看看什么是标准错误以及如何对它重定向。当命令输出错误信息时,stderr信息就会被打印出来。考虑下面的例子:
 

复制代码 代码示例:
$ Is +
Is:cannot access +:No such file or directory
 

这里,+是一个非法参数,因些将返回错误信息。
[ 成功和不成功的命令
   当一个命令发生错误并退回时,它会返回一个非0的退出状态;而当命令成功完成后,它会返回数字0。退出状态可以从特殊变量$? 中获得(在命令执行语句之后立刻运行echo$?,就可以打印出退出状态)。]

将stderr文本打印到屏幕上,而不是文件中。
 

复制代码 代码示例:
$ Is+>out.txt
Is:cannot access+:No such file or directory
 

然而在下面的命令中,stdout没有任何输出,因为错误已经重定向到out.txt中去了。
 

复制代码 代码示例:
$ Is +2> out.txt # 正常运行
 

你可以将stderr单独重定向到一个文件,将stdout重定向到另一个文件:
 

复制代码 代码示例:
$ cmd 2>stderr.txt 1>stdout.txt
 

还可以利用下面的方法将stderr转换成stdout,使得stderr和stdout都被重定向到同一个文件中:
 

复制代码 代码示例:
$ cmd 2>&1 output.txt
 

或者采用下列方法:
 

复制代码 代码示例:
$ cmd&> output.txt
 

有时候,在输出中可能包含一些不必要的信息(比如除错信息)。如果你不想让终端中充斥着有关stderr的繁枝末节,那么你可以将stderr的输出重定向到/dev/null, 保证一切都会被清除得干干净净。假设我们有三个文件,分别是a1、a2、a3。但是普通用户对a1没有“读一写一执行”权限。如果你需要打印文件名以a起始的所有文件的内容,你可以使用cat命令。
设置一些测试文件:
 

复制代码 代码示例:
$ echo a1 >a1
$ cp a1 a2;cp a2 a3;
$ chmod 000 a1 #清除所有权限
 

尽管可以使用通配符(a*)显示所有的文件内容,但是系统会显示一个出错信息,因为对文件a1没有可读权限。
 

复制代码 代码示例:
$ cat a*
cat:a1 permission denied
a1
a1
 

其中,cat:a1:permission denied 属于stderr。我们可以将stderr信息重定向到一个文件中,而stdout 仍然保持不变。考虑如下代码:
 

复制代码 代码示例:

$ cat a* 2>err.txt #stderr被重定向到err.txt
a1
a1

$ cat err.txt
cat:a1:permission denied
 

观察下面的代码:
 

复制代码 代码示例:
$ some_command 2>/dev/null
 

您可能感兴趣的文章:
玩转Linux文件描述符和重定向
make和makefile详解
&1"的含义" target="_blank">linux shell 中"2>&1"的含义
python fd是什么意思
(原创)shell中自定义文件描述符的方法介绍
shell程序设计教程(1)
shell 输出重定向用法浅析(图文)
shell脚本学习指南之输入输出与文本执行(图文)
改变文件组命令chgrp和改变文件属主命令chown
有关I/O重定向的详细教程

[关闭]
~ ~