내 데이터 파일은 다음과 같습니다.
10 -0.314690785295
20 -0.251967909317
30 -0.215271387106
40 -0.189228416217
원하는 출력은 다음과 같습니다.
10 -0.0627229
20 -0.0994193
30 -0.1254623
답변1
awk 'BEGIN {first_row = 0; col_val=""}{ if (first_row == 0) {first_row = $2; col_val=$1} else {print col_val " " first_row - $2; col_val=$1}}'
다음은 명령줄의 출력입니다.
$ echo "10 -0.314690785295
20 -0.251967909317
30 -0.215271387106
40 -0.189228416217" | awk 'BEGIN {first_row = 0; col_val=""}{ if (first_row == 0) {first_row = $2; col_val=$1} else {print col_val " " first_row - $2; col_val=$1}}'
10 -0.0627229
20 -0.0994194
30 -0.125462
좋습니다. 이제 왜 이런 일이 발생하는지 설명하겠습니다.
BEGIN 절은 시작하기 전에 초기화로 실행되는 코드 섹션을 정의합니다. 이 위치에서 나머지 로직 전체에서 추적할 두 개의 변수를 초기화합니다.
프로그램의 주요 부분에 있는 {}의 두 번째 집합에 있습니다. 입력의 각 줄에 대해 실행될 논리를 정의합니다(특정 줄에서만 실행되도록 앞에 패턴을 추가할 수도 있지만 이는 이 답변의 범위를 벗어납니다).
이 논리는 first_row 값이 설정되었는지 여부를 테스트합니다. 그렇지 않은 경우 이는 입력의 첫 번째 행입니다. first_row 값을 해당 행의 두 번째 문자열인 $2로 초기화하고 원하는 값과 일치하도록 첫 번째 열인 $1의 문자열도 복사해야 합니다. 출력, 값을 col_val에 복사합니다.
그렇지 않으면 입력의 다른 모든 행에 대해 col_value를 한 공백으로 인쇄하고 현재 행의 두 번째 위치 $2에 있는 값에서 first_row를 뺀 결과를 인쇄하므로 first_row - $2가 됩니다. 그런 다음 입력의 첫 번째 열에서 새 문자열 값을 col_val에 복사합니다.
처음으로 나는 당신에게 정말로 필요한 것이 무엇인지 이해하지 못합니다 :).. 여기에 당신이 원하는 것을 수행할 awk 스크립트가 있습니다.. 10 - 20은 10이 아닌 -10이기 때문입니다.
awk '{ if (NR == 1) { for (i = 1; i <= NF; i++){ first_row[i] = $i} } else { for (i = 1; i <= NF; i++){ printf "%s ", first_row[i] - $i }; printf "\n"}}'
출력은 다음과 같습니다. 첫 번째 열에서 예상한 것과 약간 다릅니다. 진행 상황을 표시하기 위해 다른 열을 추가했습니다.
echo "10 -0.314690785295 18
20 -0.251967909317 12
30 -0.215271387106 35
40 -0.189228416217 44" | awk '{ if (NR == 1) { for (i = 1; i <= NF; i++){first_row[i] = $i} } else { for (i = 1; i <= NF; i++){ printf "%s ", first_row[i] - $i }; printf "\n"}}'
-10 -0.0627229 6
-20 -0.0994194 -17
-30 -0.125462 -26