합격하려고 해요바꾸다쉘 스크립트에서 테이블의 패턴 인식 하위 집합까지의 인수 수입니다. 지금까지 시도한 내용은 다음과 같습니다.
파일 "infile":
ID,GROUP
1,GROUP2
2,GROUP2
3,GROUP4
4,GROUP4
5,GROUP5
6,GROUP5
7,GROUP23
8,GROUP23
9,GROUP23
파일 하위 집합.sh:
#!/bin/sh
rm -f outfile_$week
week = $1
shift
for TOKEN in "$@"
do
echo "adding records for" $TOKEN
awk -F "," -v group = $TOKEN '{ if(FNR > 2 && $2 ~/group/){print $0} }' infile >> outfile_$week
done
또한 group = "$TOKEN", "group = $TOKEN"을 시도한 다음 둘 다 작은따옴표로 시도했습니다. 나는 다음과 같이 제출합니다.
sh subset.sh 061314 GROUP2 GROUP23
오류 메시지가 거의 표시되지 않습니다.
Usage: awk [-F fs][-v Assignment][-f Progfile|Program][Assignment|File] ...
도움을 주시면 대단히 감사하겠습니다. 감사합니다!
편집: 나는 달리기를 시도했다
awk -F "," -v group ="GROUP1" '{ if(FNR > 2 && $2 ~/group/){print $0} }' infile
아무 소용이 없습니다... (위와 동일한 오류) 이런 일이 발생하는 이유를 아는 사람이 있습니까?
답변1
다음과 같이 작성해야 합니다.
-v group="$TOKEN"
대신 -v group = $TOKEN
에서 구문 오류가 발생합니다 awk
.
답변2
당신이 원하는 것 같아요 :
awk -F, '
BEGIN {
for (i = 1; i < ARGC; i++) group[ARGV[i]]
ARGC=0
}
NR >= 2 && $2 in group' "$@" < infile
또는 인수를 두 번째 열과 일치하는 정규식으로 처리하려는 경우:
awk -F, '
BEGIN {
for (i = 1; i < ARGC; i++) group[ARGV[i]]
ARGC=0
}
NR >= 2 {
for (i in group) if ($2 ~ i) {print; next}
}' "$@" < infile
답변3
직면하고 있는 즉각적인 문제는 등호 주변의 공백입니다. 이 옵션에 대한 인수는 -v
할당이어야 합니다. awk는 인수 -v
, 스크립트( =
), 파일 이름( 값 TOKEN
, 스크립트 및 파일 이름)을 확인합니다.
쉘 스크립트에서 비슷한 실수를 저질렀습니다. week = $1
이어야 합니다 week="$1"
.
그런데,명령 대체에는 항상 큰따옴표를 사용하세요.. 예를 들어 TOKEN
is 인 경우 *
현재 디렉터리의 파일 목록으로 대체됩니다.
awk -v "group=$TOKEN"
그러나 awk는 할당의 오른쪽을 awk 구문의 리터럴로 처리하기 때문에 group
값을 로 설정하지 않습니다 . TOKEN
예를 들어, 값이 TOKEN
7자 string 이면 foo\bar
awk 변수는 group
6자 string 으로 설정됩니다 foo␈ar
. 여기서 ␈
백스페이스 문자는 (바이트 값 8)입니다.
변수를 awk 스크립트에 전달하는 간단한 방법은 변수를 환경으로 내보내고 배열을 통해 사용하는 것입니다 ENVIRON
.
group
또한 awk 스크립트의 어느 곳에서도 이 변수를 사용 하지 않습니다 . 정규식은 /group/
5자 문자열을 포함하는 모든 문자열과 일치합니다 group
. 필드가 값과 정확히 같은지 확인하려면 group
(예를 들어 값이 이면 TOKEN
포함 GROUP2
된 필드가 GROUP24
일치하지 않음) 같음 연산자를 사용합니다 ==
.
export TOKEN
awk -F "," '{ if (FNR > 2 && $2 == ENVIRON["TOKEN"]){print $0} }' infile >> outfile_$week
전체 스크립트는 다음과 같습니다. awk의 조건부 작업 구문( print $0
기본값이므로 여기에서는 작업이 생략됨)을 사용하고 매번 출력 파일을 열지 않도록 더욱 단순화되었습니다.
#!/bin/sh
week="$1"
shift
for TOKEN in "$@"
do
echo "adding records for" $TOKEN
awk -F "," 'FNR > 2 && $2 == ENVIRON["TOKEN"]' infile
done >"outfile_$week"
바라보다Stefan Chazeras의 답변awk를 사용하는 고급 방법에서는 입력 파일을 여러 번 처리할 필요가 없습니다.