옵션 1 ~ 3에는 다중 공백 문제가 있습니다 (단순함). 이것이 문제없이 여러 개의 공백을 처리하는 옵션 4와 5를 개발 한 이유입니다. 물론, 옵션 4 또는 5가 n=0
둘 다 와 함께 사용 되면 n=0
분할이 없음 을 의미 하므로 선행 공백이 유지됩니다 .
옵션 1
단순 절단 솔루션 (단일 구분 기호로 작동) :
$ echo '1 2 3 4 5 6 7 8' | cut -d' ' -f4-
4 5 6 7 8
옵션 2
awk 재 계산을 강제하면 때때로 추가 된 선행 공백의 문제 (일부 버전의 awk에서 작동)가 해결됩니다.
$ echo '1 2 3 4 5 6 7 8' | awk '{ $1=$2=$3="";$0=$0;} NF=NF'
4 5 6 7 8
옵션 3
형식이 지정된 각 필드를 인쇄 printf
하면 더 많은 제어가 가능합니다.
$ echo ' 1 2 3 4 5 6 7 8 ' |
awk -v n=3 '{ for (i=n+1; i<=NF; i++){printf("%s%s",$i,i==NF?RS:OFS);} }'
4 5 6 7 8
그러나 이전의 모든 답변은 필드 간의 모든 FS를 OFS로 변경합니다. 이에 대한 몇 가지 솔루션을 구축해 보겠습니다.
옵션 4
필드와 구분 기호를 제거하는 sub가있는 루프는 더 이식성이 뛰어나며 FS를 OFS로 변경하지 않습니다.
$ echo ' 1 2 3 4 5 6 7 8 ' |
awk -v n=3 '{ for(i=1;i<=n;i++) { sub("^["FS"]*[^"FS"]+["FS"]+","",$0);} } 1 '
4 5 6 7 8
노트: "^ ["FS "] *"는 선행 공백이있는 입력을 허용합니다.
옵션 5
추가 선행 또는 후행 공백을 추가하지 않고 gensub
GNU awk 의 함수 를 사용하여 기존 공백을 유지하는 솔루션을 구축하는 것이 가능합니다 .
$ echo ' 1 2 3 4 5 6 7 8 ' |
awk -v n=3 '{ print gensub("["FS"]*([^"FS"]+["FS"]+){"n"}","",1); }'
4 5 6 7 8
또한 개수가 주어진 필드 목록을 교체하는 데 사용할 수도 있습니다 n
.
$ echo ' 1 2 3 4 5 6 7 8 ' |
awk -v n=3 '{ a=gensub("["FS"]*([^"FS"]+["FS"]+){"n"}","",1);
b=gensub("^(.*)("a")","\\1",1);
print "|"a"|","!"b"!";
}'
|4 5 6 7 8 | ! 1 2 3 !
물론 이러한 경우 OFS는 줄의 두 부분을 구분하는 데 사용되며 필드의 후행 공백은 여전히 인쇄됩니다.
참고 1 : ["FS"]*
입력 줄에 선행 공백을 허용하는 데 사용됩니다.
cut -f3-
?