我有许多结构类似但略有不同的纯文本文件,我需要从中提取特定行。
这行文本不遵循任何特定模式(即其内容总是不同),并且并不总是位于文件中的同一位置——尽管通常靠近文件的开头。
这些文件是新闻稿(最初为 PDF,使用 即时转换为文本pdftotext
),我需要提取的行是主题,之后我需要将其用作文件名。
如果我只是运行sed -n '1p'
这些文件,提取第一行,有时我会得到我想要的结果,但更多时候不会。
我得到的不同结果的示例:
Title of the press release # correct result
# wrong, here the first line is empty
29.9.2016 # wrong, here the first line contains the date
PRESS RELEASE # also wrong, I would need to scan further down
这些几乎是所有案例。让我充满希望的是,由于这些文件具有非常相似的结构,并且包含接近开头的标题,如果我继续向下扫描,迟早我会找到我要找的东西。
有什么办法告诉 sed,在同一个 sed 命令中,尝试不同的模式,直到满足一组条件不是遇见了?
就我而言,我需要告诉 sed:
- 检查该行是否为空
- 检查该行是否不包含日期
- 检查该行是否不包含“Press Release”字样
如果没有一个条件满足,则输出该行,如果满足,则跳到下一行。
这是 sed 能够做的事情吗?
答案1
查找任何形式的文本的第一行,该文本不为空(并且不仅包含空格),不只包含数字和点,也不包含字符串PRESS RELEASE
(大写):
sed '/^[[:blank:]]*$/d; /^[0-9.]*$/d; /PRESS RELEASE/d; q' file
如果日期-
中可以有 和 空格,并且 ifPRESS RELEASE
也可以写成press release
, Press Release
or Press release
(或pRESS Release
或其他一些组合):
sed -E '/^[[:blank:]]*$/d; /^[0-9. -]*$/d; /[Pp](RESS|ress) [Rr](ELEASE|elease)/d; q' file
或使用 GNU 进行sed
不区分大小写的匹配press release
:
sed '/^[[:blank:]]*$/d; /^[0-9. -]*$/d; /press release/Id; q' file
每次触发模式时,该d
命令都会从输入中删除该行,并从下一行开始新的循环。如果没有触发任何模式,则会q
导致脚本退出,但将首先打印当前行。