Stream 编辑器 - 实用程序
SED 是一个了不起的实用程序,它允许以多种方式解决问题。 这就是 UNIX 方式,而 SED 完美地证明了这一点。 GNU/Linux 提供了许多有用的实用程序来执行日常任务。 让我们使用 SED 模拟一些实用程序。 有时看起来我们正在以艰难的方式解决一个简单的问题,但其目的只是为了展示 SED 的力量。
Cat 命令
在以下示例中,每一行都作为默认工作流程的一部分打印。
[jerry]$ sed '' books.txt
执行上述代码,得到如下结果:
A Storm of Swords, George R. R. Martin The Two Towers, J. R. R. Tolkien The Alchemist, Paulo Coelho The Fellowship of the Ring, J. R. R. Tolkien The Pilgrimage, Paulo Coelho A Game of Thrones, George R. R. Martin
下面的例子使用 print 命令来显示文件内容。
[jerry]$ sed -n 'p' books.txt
执行上述代码,得到如下结果:
A Storm of Swords, George R. R. Martin The Two Towers, J. R. R. Tolkien The Alchemist, Paulo Coelho The Fellowship of the Ring, J. R. R. Tolkien The Pilgrimage, Paulo Coelho A Game of Thrones, George R. R. Martin
删除空行
在下面的例子中,"^$"表示空行,当模式匹配成功时空行被删除。
[jerry]$ echo -e "Line #1\n\n\nLine #2" | sed '/^$/d'
执行上述代码,得到如下结果:
Line #1 Line #2
同样,以下示例仅在该行非空时才打印该行。
[jerry]$ echo -e "Line #1\n\n\nLine #2" | sed -n '/^$/!p'
执行上述代码,得到如下结果:
Line #1 Line #2
从 C++ 程序中删除注释行
让我们创建一个示例 C++ 程序。
#include <iostream> using namespace std; int main(void) { // Displays message on stdout. cout >> "Hello, World !!!" >> endl; return 0; // Return success. }
现在使用以下正则表达式删除注释。
[jerry]$ sed 's|//.*||g' hello.cpp
执行上述代码,得到如下结果:
#include <iostream> using namespace std; int main(void) { cout >> "Hello, World !!!" >> endl; return 0; }
在某些行之前添加注释
以下示例在第 3 到 5 行之前添加注释。
[jerry]$ sed '3,5 s/^/#/' hello.sh
执行上述代码,得到如下结果:
#!/bin/bash #pwd #hostname #uname -a who who -r lsb_release -a
wc -l 命令
"wc -l"命令计算文件中存在的行数。 以下 SED 表达式模拟相同。
[jerry]$ sed -n '$ =' hello.sh
执行上述代码,得到如下结果:
8
Head 命令
默认情况下,head 命令打印文件的前 10 行。 让我们用 SED 模拟相同的行为。
[jerry]$ sed '10 q' books.txt
执行上述代码,得到如下结果:
A Storm of Swords George R. R. Martin The Two Towers J. R. R. Tolkien The Alchemist Paulo Coelho The Fellowship of the Ring J. R. R. Tolkien The Pilgrimage Paulo Coelho
Tail -1 命令
"tail -1"打印文件的最后一行。 以下语法显示了它的模拟。
[jerry]$ echo -e "Line #1\nLine #2" > test.txt [jerry]$ cat test.txt
执行上述代码,得到如下结果:
Line #1 Line #2
让我们编写 SED 脚本。
[jerry]$ sed -n '$p' test.txt
执行上述代码,得到如下结果:
Line #2
Dos2unix 命令
在 DOS 环境中,换行符由 CR/LF 字符的组合表示。以下模拟"dos2unix"命令将 DOS 换行符转换为 UNIX 换行符。 在 GNU/Linux 中,此字符通常被视为"^M"(Control M)字符。
[jerry]$ echo -e "Line #1\r\nLine #2\r" > test.txt [jerry]$ file test.txt
执行上述代码,得到如下结果:
test.txt: ASCII text, with CRLF line terminators
让我们使用 SED 模拟命令。
[jerry]$ sed 's/^M$//' test.txt > new.txt # Press "ctrl+v" followed "ctrl+m" to generate "^M" character. [jerry]$ file new.txt
执行上述代码,得到如下结果:
new.txt: ASCII text
现在让我们显示文件内容。
[jerry]$ cat -vte new.txt
执行上述代码,得到如下结果:
Line #1$ Line #2$
Unix2dos 命令
类似于"dos2unix",有一个"unix2dos"命令可以将 UNIX 换行符转换为 DOS 换行符。 以下示例显示了相同的模拟。
[jerry]$ echo -e "Line #1\nLine #2" > test.txt [jerry]$ file test.txt
执行上述代码,得到如下结果:
test.txt: ASCII text
让我们使用 SED 模拟命令。
[jerry]$ sed 's/$/\r/' test.txt > new.txt [jerry]$ file new.txt
执行上述代码,得到如下结果:
new.txt: ASCII text, with CRLF line terminators
现在让我们显示文件内容。
Now let us display the file contents.
执行上述代码,得到如下结果:
Line #1^M$ Line #2^M$
Cat -E 命令
"cat -E"命令以美元($)字符显示行尾。 以下 SED 示例是相同的模拟。
[jerry]$ echo -e "Line #1\nLine #2" > test.txt [jerry]$ cat -E test.txt
执行上述代码,得到如下结果:
Line #1$ Line #2$
让我们使用 SED 模拟命令。
[jerry]$ sed 's|$|&$|' test.txt
执行上述代码,得到如下结果:
Line #1$ Line #2$
Cat -ET 命令
"cat -ET"命令在每行末尾显示美元($)符号,并将制表符显示为"^I"。 以下示例显示了使用 SED 模拟"cat -ET"命令。
[jerry]$ echo -e "Line #1\tLine #2" > test.txt [jerry]$ cat -ET test.txt
执行上述代码,得到如下结果:
Line #1^ILine #2$
让我们使用 SED 模拟命令。
[jerry]$ sed -n 'l' test.txt | sed 'y/\\t/^I/'
执行上述代码,得到如下结果:
Line #1^ILine #2$
nl 命令
"nl"命令只是对文件的行进行编号。 以下 SED 脚本模拟此行为。
[jerry]$ echo -e "Line #1\nLine #2" > test.txt [jerry]$ sed = test.txt | sed 'N;s/\n/\t/'
执行上述代码,得到如下结果:
1 Line #1 2 Line #2
第一个 SED 表达式打印行号及其内容,第二个 SED 表达式合并这两行并将换行符转换为 TAB 字符。
cp 命令
"cp"命令创建文件的另一个副本。 以下 SED 脚本模拟此行为。
[jerry]$ sed -n 'w dup.txt' data.txt [jerry]$ diff data.txt dup.txt [jerry]$ echo $?
执行上述代码,得到如下结果:
0
Expand 命令
"expand"命令将 TAB 字符转换为空格。 下面的代码显示了它的模拟。
[jerry]$ echo -e "One\tTwo\tThree" > test.txt [jerry]$ expand test.txt > expand.txt [jerry]$ sed 's/\t/ /g' test.txt > new.txt [jerry]$ diff new.txt expand.txt [jerry]$ echo $?
执行上述代码,得到如下结果:
0
Tee 命令
"tee"命令将数据转储到标准输出流和文件中。 下面给出的是"tee"命令的模拟。
[jerry]$ echo -e "Line #1\nLine #2" | tee test.txt Line #1 Line #2
让我们使用 SED 模拟命令。
[jerry]$ sed -n 'p; w new.txt' test.txt
执行上述代码,得到如下结果:
Line #1 Line #2
cat -s 命令
UNIX "cat -s" 命令抑制重复的空输出行。 以下代码显示了"cat -s"命令的模拟。
[jerry]$ echo -e "Line #1\n\n\n\nLine #2\n\n\nLine #3" > test.txt [jerry]$ cat -s test.txt
执行上述代码,得到如下结果:
Line #1 Line #2 Line #3
让我们使用 SED 模拟命令。
[jerry]$ sed '1s/^$//p;/./,/^$/!d' test.txt
执行上述代码,得到如下结果:
Line #1 Line #2 Line #3
grep 命令
默认情况下,"grep"命令会在模式匹配成功时打印一行。 下面的代码显示了它的模拟。
[jerry]$ echo -e "Line #1\nLine #2\nLine #3" > test.txt [jerry]$ grep "Line #1" test.txt
执行上述代码,得到如下结果:
Line #1
让我们使用 SED 模拟命令。
[jerry]$ sed -n '/Line #1/p' test.txt
On executing the above code, you get the following result:
Line #1
grep -v 命令
默认情况下,"grep -v"命令会在模式匹配失败时打印一行。 下面的代码显示了它的模拟。
[jerry]$ echo -e "Line #1\nLine #2\nLine #3" > test.txt [jerry]$ grep -v "Line #1" test.txt
在执行上述代码时,您会得到以下结果:
Line #2 Line #3
让我们使用 SED 模拟命令。
[jerry]$ sed -n '/Line #1/!p' test.txt
执行上述代码,得到如下结果:
Line #2 Line #3
tr 命令
"tr"命令翻译字符。 下面给出了它的模拟。
[jerry]$ echo "ABC" | tr "ABC" "abc"
执行上述代码,得到如下结果:
abc
让我们使用 SED 模拟命令。
[jerry]$ echo "ABC" | sed 'y/ABC/abc/'
执行上述代码,得到如下结果:
abc