내 입력 File1은 다음과 같습니다.
A,22,1,2,3,4,5
G,26,5,6,7
X,28,10,20,10
파일 구조를 유지하면서 3열에 수식을 적용하고 싶습니다. 예를 들어 방정식에 2를 곱하려는 경우 출력을 찾습니다.
A,22,2,4,6,8,10
G,26,10,12,14
X,28,20,40,20
이를 위해 다음 명령을 사용해 보았습니다.
awk -F ',' '{for(i=1; i<=NF; i++) if (i >= 3)
print 2*$i
else
print $i }' File1
이는 올바른 출력을 제공하지만 모든 파일 구조를 제거합니다. 내가 사용하고 싶은 실제 방정식을 사용하는 경우: 2*(2*($i-1)+1)
솔루션과 함께 제공되는 설명은 아직 매우 익숙하지 않기 때문에 크게 감사하겠습니다!
답변1
OFS
예를 들어 출력 필드 구분 기호( )만 설정하면 됩니다 .
awk '{ for (i=3; i<=NF; i++) $i*=2 } 1' FS=, OFS=, infile
또는 다음 공식을 사용하세요.
awk '{ for (i=3; i<=NF; i++) $i = 2*(2*($i-1)+1) } 1' FS=, OFS=, infile
산출:
A,22,2,4,6,8,10
G,26,10,12,14
X,28,20,40,20
스크립트 끝에는 1
다음의 약어가 있습니다.{ print $0 }
답변2
Perl
이 문제는 다음과 같이 해결될 수 있습니다. @Thor의 제안에 따라:
$ perl -F, -anE '$,="," ; say splice(@F,0,2), map { 2*(2*($_-1)+1) } @F' inp.csv
다른 방법을 사용하십시오:
$ perl -lpe '
/^[^,]*,[^,]*/g; #positions the search engine before the 2nd comma.
s/\G,\K([^,]*)/2*(2*($1-1)+1)/ge;
' inp.csv
GNU 데스크탑 계산기 유틸리티는 다음을 수행할 수 있습니다:
$ < inp.csv tr ',-' ' _' | sed -Ee 's/\S+/[&]/' |
dc -e "
[q]sq
[44an]s,
[1-2*1+2*]s=
[SM lN1+sN z0<a]sa
[LMnl,x LMnl,x lN2-sN]sb
[LMl=xn lN1<, lN1-dsN0<c]sc
[?z0=q 0sN lax lbx lcx 10an z0=?]s?
l?x
"
간단하고 명확한 코드이므로 요청에 따른 간단한 유틸리티 및 설명입니다.
간략한 설명:
이 dc
유틸리티는 데이터와 코드가 저장되는 스택에서 작동합니다. 여기에서 n개의 검색을 레지스터에 저장합니다.
문자열 데이터는 대괄호로 묶입니다.
삭제는 재귀적으로 수행됩니다.
이 dc 코드에는 코드를 저장하는 7개의 레지스터, 즉 q = , abc ?
두 개의 레지스터 MN은 데이터를 저장합니다.
끝부터 시작하여 거꾸로 작업하세요. 코드등록? 입력에서 다음 줄을 읽는 작업을 수행합니다. 그런 다음 스택에 공백으로 구분된 항목이 몇 개 있는지 비교합니다. 0이면 중지하고 종료합니다. z0=q 조각이 바로 그 일을 합니다. 다음과 같이 읽습니다. z는 존재하는 요소 수를 반환하는 dc 명령입니다. 0과 비교하여 같으면 레지스터 q에 저장된 코드를 실행합니다.
답변3
s=`awk '{print NR}' p.txt| sort -nr | sed -n '1p'`
praveen@praveen:~$ for ((i=1;i<=$s;i++)); do m=`awk -v i="$i" -F "," 'NR==i{print NF}' p.txt`; for ((u=1;u<=$m;u++)); do if [[ $u < 3 ]]; then awk -v i="$i" -v u="$u" -F "," 'NR==i{print $u}' p.txt; else awk -v i="$i" -v u="$u" -F "," 'NR==i {print 2*$u}' p.txt; fi; done| sed "N;s/\n/,/g"| sed "N;s/\n/,/g"| sed "N;s/\n/,/g"; done
where p.txt is filename
A,22,2,4,6,8,10
G,26,10,12,14
X,28,20,40,20