나는 보통 텍스트를 사용하여 메모를 작성하는 데 사용하는 텍스트 파일이 있습니다 cat >> file
. 때때로 나는 빈 줄이나 두 줄을 사용하여 (새 줄 문자 만 반환) 새로운 주제 / 생각을 지정합니다. 각 세션이 끝나면 Ctrl+로 파일을 닫기 전에 D일반적으로 세션을 분리하기 위해 많은 (5-10) 개의 빈 줄 (return-key)을 추가합니다.
이것은 분명히 영리하지는 않지만이 목적으로 저에게 효과적입니다. 내가 할 최종 최대 그러나 많은 불필요한 빈 줄이 많은, 내가 제거하는 방법을 찾고 있어요 그래서 여분의 라인 (대부분). 몇 가지 옵션으로 직접 사용할 수있는 Linux 명령 (cut, paste, grep, …?)이 있습니까? 또는 sed, awk 또는 perl에 대한 아이디어가 있습니까? C ++로 무언가를 작성하면 (실제로 스스로 할 수 있음) 과잉처럼 보입니다.
사례 # 1 : 필요한 것은 연속 된 빈 줄을 두 개 이상 제거하고 두 개의 빈 줄로 바꾸는 스크립트 / 명령입니다. 하나 이상의 줄을 제거하거나 (2 개 이상) 여러 개의 빈 줄을 하나의 빈 줄로 바꾸는 것도 좋은 방법입니다.
사례 # 2 : 두 줄의 텍스트 사이 에서 하나의 빈 줄을 제거하는 스크립트 / 명령을 사용할 수도 있지만 여러 줄을 그대로 둡니다 (빈 줄 중 하나를 제거해도됩니다).
답변
사례 1 :
awk '!NF {if (++n <= 2) print; next}; {n=0;print}'
사례 2 :
awk '!NF {s = s $0 "\n"; n++; next}
{if (n>1) printf "%s", s; n=0; s=""; print}
END {if (n>1) printf "%s", s}'
답변
uniq
빈 줄의 여러 인스턴스를 하나의 빈 줄로 축소하는 데 사용할 수 있지만 텍스트가 같은 줄과 서로 아래 인 경우 줄이 축소됩니다.
답변
사례 1 :
perl -i -ane '$n=(@F==0) ? $n+1 : 0; print if $n<=2'
사례 2 :
perl -i -ane '$n=(@F==0) ? $n+1 : 0; print $n==2 ? "\n$_" : $n==1 ? "" : $_ '
답변
GNU sed를 사용하여 사례 1을 다음과 같이 해결할 수 있습니다.
sed -r ':a; /^\s*$/ {N;ba}; s/( *\n *){2,}/\n\n/'
즉, 패턴 공간에서 빈 줄을 수집하고 3 개 이상의 줄이 있으면 두 줄로 줄이십시오.
사례 # 2에서와 같이 단일 공백 행을 결합하려면 다음과 같이 수행하십시오.
sed -r '/^ *\S/!b; N; /\n *$/!b; N; /\S *$/!b; s/\n *\n/\n/'
또는 주석이 달린 형식으로 :
sed -r '
/^ *\S/!b # non-empty line
N #
/\n *$/!b # followed by empty line
N #
/\S *$/!b # non-empty line
s/\n *\n/\n/ # remove the empty line
'
답변
이 솔루션은 파일의 마지막 빈 줄도 처리합니다.
sed -r -n '
/^ *$/!{p;b} # non-blank line - print and next cycle
h # blank line - save it in hold space
:loop
$b end # last line - go to end
n # read next line in pattern space
/^ *$/b loop # blank line - loop to next one
:end # pattern space has non-blank line or last blank line
/^ *$/{p;b} # last blank line: print and exit
H;x;p # non-blank line: print hold + pattern space and next cycle
'
답변
“uniq”를 사용하기위한 Anthon 의 제안에 따라 …
선행, 후행 및 빈 줄을 제거합니다.
# Get large random string.
rand_str=; while [[ ${#rand_str} -lt 40 ]]; do rand_str=$rand_str$RANDOM; done
# Add extra lines at beginning and end of stdin.
(echo $rand_str; cat; echo $rand_str) |
# Convert empty lines to random strings.
sed "s/^$/$rand_str/" |
# Remove duplicate lines.
uniq |
# Remove first and last line.
sed '1d;$d' |
# Convert random strings to empty lines.
sed "s/$rand_str//"
하나의 긴 줄에서 :
(rand_str=; while [[ ${#rand_str} -lt 40 ]]; do rand_str=$rand_str$RANDOM; done; (echo $rand_str; cat; echo $rand_str) | sed "s/^$/$rand_str/" | uniq | sed '1d;$d' | sed "s/$rand_str//")
또는 “cat -s”를 사용하십시오.
더 효율적인 현재 쉘 컨텍스트 를 유지하기 위해 괄호에서 중괄호로 전환했습니다 . 중괄호에는 마지막 명령 후 세미콜론이 필요하며 분리 할 공간이 필요합니다.
# Add extra blank lines at beginning and end.
# These will be removed in final step.
{ echo; cat; echo; } |
# Replace multiple blank lines with a single blank line.
cat -s |
# Remove first and last line.
sed '1d;$d'
한 줄로.
{ { echo; cat; echo; } | cat -s | sed '1d;$d'; }
답변
게시 된 솔루션은 나에게 조금 비밀스러워 보였다. 다음은 Python 3.6의 솔루션입니다.
#!/usr/bin/env python3
from pathlib import Path
import sys
import fileinput
def remove_multiple_blank_lines_from_file(path, strip_right=True):
non_blank_lines_out_of_two_last_lines = [True, True]
for line in fileinput.input(str(path), inplace=True):
non_blank_lines_out_of_two_last_lines.pop(0)
non_blank_lines_out_of_two_last_lines.append(bool(line.strip()))
if sum(non_blank_lines_out_of_two_last_lines) > 0:
line_to_write = line.rstrip() + '\n' if strip_right else line
sys.stdout.write(line_to_write)
def remove_multiple_blank_lines_by_glob(rglob='*', path=Path('.'), strip_right=True):
for p in path.rglob(rglob):
if p.is_file():
try:
remove_multiple_blank_lines_from_file(p, strip_right=strip_right)
except Exception as e:
print(f"File '{p}' was not processed due the error: {e}")
if __name__ == '__main__':
remove_multiple_blank_lines_by_glob(sys.argv[1], Path(sys.argv[2]), next(iter(sys.argv[3:]), None) == '--strip-right')
다음과 같이 인터프리터에서 함수를 호출하거나 쉘에서 실행할 수 있습니다.
$ ./remove_multiple_lines.py '*' /tmp/ --strip-right