템플릿 A.tsv(필드 구분 기호=\t)가 있습니다.
Name data
B.txt 및 C.txt와 같은 여러 파일도 있습니다.
다음과 같이 파일 이름에 (그러나 새 파일에) 파일 이름을 인쇄하고 싶습니다.
Name data
B
C
나는 이것을 했다:
template="A.tsv"
for bla in data/*.txt ; do
r="$(basename -s ".txt" $bla)"
( head -n 1 $template
awk -F'\t' -v OFS="\t" -v filename=$r '{print filename}' $bla ) > test_name.tsv ;
done
하지만 그것은 나에게 다음을 제공합니다:
Name data
C
C
C
C
C
C
C
내 명령에 어떤 문제가 있는지 아시나요?
감사해요
답변1
자세한 설명이 포함된 스크립트:
#!/bin/bash
#using the template variable is redundant, but
#I assume you want to use that lateron
template="A.tsv"
#write header from template and create file "output.txt"
#overwrites old version of "output.txt" if existing
head -n 1 ${template} > output.txt
#loop over files:
for bla in data/*.txt ; do
#get basename without file suffix, add result to "output.txt"
basename -s ".txt" ${bla} >> output.txt
done
${variable}
특히 파일 이름에는 또는 를 사용하는 것이 좋습니다 "$varaible"
. 그렇지 않으면 파일 이름에 공백 등이 포함되어 있으면 스크립트가 중단됩니다.
왜 awk
- 방법이 실패했나요?
awk
행 단위로 실행됩니다. 귀하의 코드에는 다음이 있습니다.
awk -v variable=$r '{print variable}' ${file}
따라서 10줄이 포함된 파일이 있으면 위 명령이 10번 실행되어 10줄의 변수가 생성됩니다. awk
한 번 실행한 후 중지 하려면 exit
명령을 실행해야 하는 줄을 사용하거나 지정하세요.
#execute command only on line no. 1
awk 'NR == 1 { print $1 }' file
#execute command and quit awk
awk '{ print 1 ; exit }'
원본 스크립트가 또 어디에서 실패했습니까?
>>
출력은 파일에 추가되어 >
덮어쓰게 됩니다. 스크립트에는 다음을 포함하는 루프가 있습니다.
( head -n 1 $template
awk [...] $bla ) > test_name.tsv
의 모든 일치 항목에 대해 data/*txt
이 명령이 실행되어 이전 버전을 덮어쓰고 test_name.tsv
마지막 버전만 실행됩니다. 루프가 실행될 때마다 헤더를 다시 작성하는 방법에 유의하세요.