빈 줄로 구분된 여러 단락이 있는 파일이 있습니다. 기술적으로 이는 단락이 아니라 빈 줄로 구분된 텍스트 섹션입니다.
말하자면 빈 줄 다음에 각 줄의 첫 번째 줄에 숫자를 삽입하여 단락에 번호를 매기고 싶습니다. 따라서 내 파일에 다음과 같은 내용이 있으면
이것은 텍스트입니다. 이것은 더 많은 텍스트입니다. 더 많은 텍스트! 이것은 섹션 2의 텍스트입니다. 좀 더 많은 텍스트. 당신은 요점을 이해합니다 ...
나는 이렇게 말하고 싶다:
1텍스트입니다 이게 더 많은 텍스트야 더 많은 텍스트! 2이것은 섹션 2의 텍스트입니다. 좀 더 많은 텍스트. 당신은 요점을 이해합니다 ...
답변1
bash 내장 명령으로 이것을 시도해 보세요:
#!/bin/bash
l=1 # paragraph counter
echo -n $l # print paragraph counter without new line
while read x; do # read current line from file, see last line
if [[ $x == "" ]]; then # empty line?
echo # print empty line
read x # read next line from file, see last line
((l++)) # increment paragraph counter
echo -n $l # print paragraph counter without new line
fi
echo "$x" # print current line
done < file
답변2
일반적으로 텍스트 구문 분석에 셸을 사용하는 것은 매우 느리고 번거롭습니다. 다음은 몇 가지 다른 옵션입니다.
"단락 모드"의 Perl
perl -00pe 's/^/$./' file
설명
즉,
-00
"줄"이 연속적인 단락으로 정의되는 단락 모드를 켭니다 .\n\n
는s/^/$./
줄의 시작(^
)을 현재 "줄"(단락) 번호로 바꿉니다$.
. Perl 은-p
주어진 스크립트를 실행한 후 입력 파일의 각 줄을 인쇄하도록 지시합니다-e
.앗
awk -vRS='\n\n' -vORS='\n\n' '{print NR$0}' file
설명
-vRS='\n\n'
awk의 레코드 구분 기호를 연속적인 개행 문자로 설정합니다. Perl의 단락 모드와 마찬가지로 이는 단락을 "줄"로 처리합니다. 그런 다음 현재 줄 번호(NR
)와 현재 "줄"을 인쇄하도록 지시합니다$0
. 출력 레코드 구분 기호를 연속적인 개행 문자로 설정-vORS=
하여 출력에서도 단락이 빈 줄로 구분되도록 합니다. 출력 끝에 2개의 빈 줄이 추가됩니다. 이를 방지하려면 다음을 사용할 수 있습니다head
.awk -v RS='\n\n' -vORS='\n\n' '{print NR$0}' file | head -n -2
비교해 보면, 10M 테스트 파일에서 실행할 때 다양한 솔루션이 내 시스템에서 소요되는 시간은 다음과 같습니다.
$ time a.sh > /dev/null ## a.sh is Cyrus's solution
real 0m1.419s
user 0m1.308s
sys 0m0.104s
$ time perl -00pe 's/^/$./' file > /dev/null
real 0m0.087s
user 0m0.084s
sys 0m0.000s
$ time awk -v RS='\n\n' -vORS='\n\n' '{print NR$0}' file | head -n -2 >/dev/null
real 0m0.074s
user 0m0.056s
sys 0m0.020s
위에서 볼 수 있듯이 Perl 및 awk 솔루션은 모두 쉘 접근 방식보다 훨씬 빠릅니다.