Linux Sed 教程:Sed 分支操作的 6 个示例

与任何其他编程语言一样,sed 也提供了特殊的分支命令来控制程序的流程。

在本文中,让我们回顾以下两种类型的 Sed 分支。

  • Sed 无条件分支
  • Sed 条件分支

Sed 无条件分支语法:

$ sed ':label command(s) b label'
  • :label – 标签规范。
  • commands – 任何 sed 命令
  • label – 标签的任何名称
  • b 标签——不检查任何条件就跳转到标签。 如果未指定标签,则跳转到脚本的末尾。

Sed 条件分支语法:

$ sed ':label command(s) t label'
  • :label – 标签规范。
  • commands – 任何 sed 命令
  • label – 标签的任何名称
  • t 标签——仅当最后一个替换命令修改了模式空间时才跳转到标签。 如果未指定标签,则跳转到脚本的末尾。

创建示例测试文件

让我们首先创建将在下面提到的示例中使用的 zadmei_sed.txt 文件。

Linux
        Administration
        Scripting
                Tips and Tricks
Windows
        Administration
Database
        Administration of Oracle
        Administration of Mysql
Security
        Network
                 Online\
        Security
Productivity
        Google Search\
        Tips
        "Web Based Time Tracking,
        Web Based Todo list and
        Reduce Key Stores etc"

查看文件内容如下所示

Linux Sed 教程:Sed 分支操作的 6 个示例

无条件分支的 Sed 示例

Sed 示例 1. 替换整个文件中第一次出现的模式

在文件 zadmei_sed.txt 中,将第一次出现的“Administration”替换为“Supervision”。

$ sed '/Administration/{
 s/Administration/Supervision/
 :loop
 n
 b loop
 }' zadmei_sed.txt

我们看一下结果

Linux Sed 教程:Sed 分支操作的 6 个示例

  • 在上面的 sed 命令中,它只是逐行读取并打印模式空间,直到匹配到 Administration
  • 一旦匹配到 Administration,将 Administration 替换为 Supervision(仅出现一次,注意没有“g”标志替代)。
  • 一旦第一次匹配被替换,只需读取剩余的文件内容并打印。
    • n 是一个 sed 命令,它打印模式空间并用下一行覆盖它。
    • 使用 loop 作为标签。 n 打印当前行并用下一行覆盖模式空间。 b 循环再次跳转到 :loop。 所以这个循环打印 zadmei_sed.txt 的剩余内容。

sed 示例 2. 删除整个文件中模式双引号 “” 之间的数据

在我们的示例文件中,“” 之间有三行。

$ sed -e ':loop
$!{
N
/\n$/!b loop
}
s/\"[^\"]*\"//g' zadmei_sed.txt

看下面的运行结果

Linux Sed 教程:Sed 分支操作的 6 个示例

  • 上面的命令 keep 追加文件的所有行,直到文件结束。
    • $! – 如果它不是文件结尾。
    • N – 附加下一行,模式空间由 \n 分隔
    • /\n$/!b loop ——如果这不是文件的最后一行,则再次跳转到循环。
  • 现在所有的行都将在由换行符分隔的模式空间中可用。 用空替换“”之间所有出现的数据。

Sed 示例 3. 删除文件的 HTML 标签

比方说,我有一个包含以下 html 内容的文件

<html><body>
<table
border=2><tr><td valign=top
align=right>1.</td>
<td>Line 1 Column 2</
td>
</table>
</body></html>

以下 sed 命令从给定文件中删除所有 html 标记

$ sed '/</{
:loop
s/<[^<]*>//g
/</{
N
b loop
}
}' index.html

看下面的运行结果

Linux Sed 教程:Sed 分支操作的 6 个示例

  1. 每次发现一行包含'<‘,首先删除该行的所有HTML标签。
  2. 如果现在模式空间包含“<”,这意味着一个多行标签。 现在重复以下循环:
  • 加入下一行
  • 删除所有 HTML 标记,直到不存在单个“<”
  1. 当模式空间中不存在“<”时,我们将其打印出来并开始一个新的循环。

条件分支的 Sed 示例

Sed 示例 4. 如果一行以反斜杠结尾,则将下一行添加到该行

我们的示例文件有两行以反斜杠结尾,现在我们必须将其下一行附加到它。

$ sed '
:loop
/\\$/N
s/\\\n */ /
t loop' zadmei_sed.txt

看下面的运行结果

Linux Sed 教程:Sed 分支操作的 6 个示例

  1. 检查该行是否以反斜杠 (/\\$/) 结尾,如果是,则读取下一行并将其附加到模式空间,并将行尾的 \\ 和后面的空格数替换为单个 空格。
  2. 如果替换成功,重复上述步骤。 只有替换成功时才会执行分支。
  3. 条件分支主要用于递归模式。

Sed 示例 5. comify 一个数字字符串

$ sed '
 :loop
 s/\(.*[0-9]\)\([0-9]\{3\}\)/\1,\2/
 t loop'
12342342342343434
12,342,342,342,343,434

看下面的结果

Linux Sed 教程:Sed 分支操作的 6 个示例

  1. 将数字分成两组。
  2. 第一组是直到最后三位的所有数字。 最后三位数字在第二组中被捕获。
  3. 然后两个匹配的组用逗号分隔。 然后将相同的规则一次又一次地应用于该行,直到所有数字都被分组为三个一组。
  4. 例如,在第一次迭代中,它将是 12342342342343,434
  5. 在下一次迭代 12342342342,343,434 中,直到少于三位数。

Sed 示例 6. 格式化:将行的每个前导空格替换为“+”

$ sed '
s/^ */&\n/
:loop
s/^\n//;s/ \n/\n+/
t loop' zadmei_sed.txt

看下面的运行结果

Linux Sed 教程:Sed 分支操作的 6 个示例

  1. 用换行符分隔行的所有前导空格和其他字符。
  2. 现在用换行符和 + 替换空格和换行符。 因此,从右到左的空格将被替换为 + 并且换行符将向左移动一个字符。
  3. 最后在行的开头 \n 将在那里,因此删除该新行。