X에서 Y까지의 줄에만 표시되는 중복 줄을 제거하고 파일을 제자리에서 변경하려면 어떻게 해야 합니까?
예를 들어, 10행에서 20행까지 중복된 행만 제거하려는 경우입니다.
답변1
GNU 사용 awk
(4.1.0 이상 inplace
확장 1):
gawk -i /usr/share/awk/inplace.awk '
NR >= 10 && NR <= 20 {
if ($0 in seen) next
seen[$0]
}
{print}' ./file
또는 다음을 사용하여 perl
:
perl -ni -e 'print if $. < 10 or $. > 20 or !$seen{$_}++' ./file
여러 파일 처리:
gawk -i /usr/share/awk/inplace.awk '
BEGINFILE{delete seen}
FNR >= 10 && FNR <= 20 {
if ($0 in seen) next
seen[$0]
}
{print}' ./*.txt
또는 다음을 사용하여 perl
:
perl -ni -e '
print if $. < 10 or $. > 20 or !$seen{$_}++;
if (eof) {close ARGV; undef %seen}' ./*.txt
^사용하지 마세요-i inplace
현재 작업 디렉터리(as or)에서 확장 기능을 먼저 gawk
로드 하려고 하면 누군가가 해당 디렉터리에 악성 코드를 심었을 수 있습니다. 시스템과 함께 제공되는 확장 프로그램 의 경로 는 다를 수 있습니다. 출력을 참조하세요.inplace
inplace
inplace.awk
inplace
gawk
gawk 'BEGIN{print ENVIRON["AWKPATH"]}'
답변2
awk
당신의 친구입니다
awk '{
if(NR>=10 && NR<=20)
{
if($0 in record){
next
}else{
print;
record[$0];
}
}
else{
print
}
}' file > temp && mv temp file
답변3
OP가 10~20개 행 내의 중복 행을 삭제해야 하는 경우:
sed -i '
:a; 10,19!b; N; s/\(^\|\n\)\([^\n]*\)\n\(\(.\+\n\|\)\2$\)/\1\3/; ba
' file1 file2 ...
답변4
Perl 기반 답변에 적용된 동일한 트릭을 사용하여 Awk 코드를 단축할 수도 있으며 결과적으로 더 작고 깔끔해집니다.
awk 'NR < 10 || NR > 20 || !seen[$0]++'
^ ^ ^ ^
| | | |
| \__________\___________\______ no sigil noise
|
\_ no options here to remember
(unless we want that Gawk inplace semantics)
범위가 10줄로 제한되어 있고 GNU Awk에는 어쨌든 큰 정수가 있기 때문에 카운터가 오버플로되지 않습니다.