我正在尝试通过删除重复的空行来压缩文本文档,使用sed
. 这就是我正在做的(无济于事):
sed -i -E 's/\n{3,}/\n/g' file.txt
根据本手册,我知道这是不正确的,但我不知道如何正确地做到这一点。谢谢。
我认为您想用单个空行替换多个空行的跨度,即使您的示例用\n
单个\n
而不是\n\n
. 考虑到这一点,这里有两个解决方案:
sed '/^$/{ :l
N; s/^\n$//; t l
p; d; }' input
在 sed 的许多实现中,这可以全部在一行上,嵌入的换行符被替换为;
.
awk 't || !/^$/; { t = !/^$/ }'
正如上面所建议的 Tripleee,我使用 Perl 而不是sed
:
perl -0777pi -e 's/\n{3,}/\n\n/g'
使用翻译功能
tr -s '\n'
-s 或 --squeeze-repeats 将重复字符序列减少为单个实例。
由tr -s '\n'
or处理得更好cat -s
,但如果您坚持使用sed
,这里有一个来自 GNU sed 手册第 4.17 节的示例:
#!/usr/bin/sed -f
# on empty lines, join with next
# Note there is a star in the regexp
:x
/^\n*$/ {
N
bx
}
# now, squeeze all '\n', this can be also done by:
# s/^\(\n\)*/\1/
s/\n*/\
/
我不确定这是 OP 想要的,但如果您想删除文件中的所有空行,则使用 William Pursell 的 awk 解决方案是一种方法:
awk '!/^$/' file.txt
解释:
awk 模式
'!/^$/'
正在测试当前行是否仅由行首(用'^'表示)和行尾(用'$'表示)组成,换句话说,该行是否为空。
如果此模式为真,则 awk 应用其默认值并打印当前行。
高温高压
我认为 OP 想要压缩空行,例如,如果有 9 个连续的空行,他想要只有三个。我已经编写了一个小 bash 脚本来做到这一点:
#! /bin/bash
TOTALLINES="$(cat file.txt|wc -l)"
CURRENTLINE=1
while [ $CURRENTLINE -le $TOTALLINES ]
do
L1=$CURRENTLINE
L2=$(($L1 + 1))
L3=$(($L1 +2))
if [[ $(cat file.txt|head -$L1|tail +$L1) == "" ]]||[[ $(cat file.txt|head -$L1|tail +$L1) == " " ]]
then
L1EMPTY=true
else
L1EMPTY=false
fi
if [[ $(cat file.txt|head -$L2|tail +$L2) == "" ]]||[[ $(cat file.txt|head -$L2|tail +$L2) == " " ]]
then
L2EMPTY=true
else
L2EMPTY=false
fi
if [[ $(cat file.txt|head -$L3|tail +$L3) == "" ]]||[[ $(cat file.txt|head -$L3|tail +$L3) == " " ]]
then
L3EMPTY=true
else
L3EMPTY=false
fi
if [ $L1EMPTY = true ]&&[ $L2EMPTY = true ]&&[ $L3EMPTY = true ]
then
#do not cat line to temp file
echo "Skipping line "$CURRENTLINE
else
echo "$(cat file.txt|head -$CURRENTLINE|tail +$CURRENTLINE)">>temp.txt
echo "Writing line " $CURRENTLINE
fi
((CURRENTLINE++))
done
cat temp.txt>file.txt
rm -r temp.txt
FINALTOTALLINES="$(cat file.txt|wc -l)"
EMPTYLINELINT=$(( $CURRENTLINE - $FINALTOTALLINES ))
echo "Deleted " $EMPTYLINELINT " empty lines."