awk를 사용한 표준 편차

awk를 사용한 표준 편차

다음 명령을 사용하여 파일 A 이름의 표준 편차를 얻습니다.

   1 2 3 평균
23.3107 20.0372 21.7236 21.6905

awk '{x[NR]=$0 ;} END{a=$4; for (i in x){ss += (x[i]-a)^2} sd = sqrt(ss/n); SD}'

치명적이 됨: 0으로 나누어 보세요.

위 명령을 다음과 같이 수정하세요.

awk '{x[NR]=$0 ;} END{a=$4; for (i in x){if (a == 0) $6 ="N/A" 그렇지 않으면 ss += (x[i]-a )^2} sd = sqrt(ss/n) 인쇄 $5 = sd}'

그런데 오류가 여전히 존재하나요? 고마워요 캐스. 제가 추구하는 바를 이해하시나요?

답변1

"n"은 어디에 있나요?

당신은 쓰기:

sd = sqrt(ss/n)

그런데 코드의 어디에 변수 "n"을 할당했습니까? 표면적으로 awk"n"은 0입니다.

또한 열 5 a=$5(세 번째 질문, 이 과제가 이 END섹션에 있는 이유)는 어디에 있나요? 귀하의 예에는 4개의 열만 포함되어 있습니다.

답변2

이런 걸 하고 싶나요? 이것이 귀하의 스크립트를 이해하기 위해 제가 생각할 수 있는 유일한 방법입니다.

awk -v OFS=$'\t' '
FNR == 1 { $5 = "sdev" ; print }

FNR > 1  { a = $4    # field 4 is 'avg'
           n = NF-1  # exclude the 'avg' field from the ss calculations.

           for (i=1; i <= n; i++) { ss += ($i - a)^2 } 

           $5 = sqrt(ss/n)
           print
         }' inputfile

참고: $i이 줄은 for값을 참조하지 i않고 번호가 매겨진 입력 필드를 참조합니다 . 즉 , , 및 을 i반복합니다 . (스칼라) 변수에는 일반적으로 접두사가 붙기 때문에 이는 쉘이나 사용자에게 명확하지 않을 수 있습니다 .$1$2$3perl$

NF는 한 줄의 필드 수이고 는 FNR현재 입력 파일의 레코드(줄) 번호입니다. 따라서 이 awk스크립트는 각각 고유한 헤더 줄이 있는 여러 입력 파일을 지원합니다. 한 번에 하나의 입력 파일만 있는 경우 NR대신 사용할 수 있습니다 FNR.

예제 출력:

1       2       3       avg     sdev
23.3107 20.0372 21.7236 21.6905 1.33661

행당 필드 수에 관계없이 작동하는 또 다른 버전은 다음과 같습니다. 그것은 가정한다마지막행의 필드에는 해당 행에 있는 모든 이전 필드의 평균이 포함됩니다.

$NF마지막 필드의 값(예: "avg")을 참조하고 $new(마지막 필드 + 1)을 참조합니다. 즉, 값을 할당하면 줄 끝에 새 필드가 추가됩니다.

awk -v OFS=$'\t' '
FNR == 1 { new = NF+1   # number of new field to add
           $new = "sdev"
           print 
         }

FNR > 1  { a = $NF   # last field is 'avg'
           n = NF-1  # exclude the 'avg' field from the ss calculations.

           for (i=1; i <= n; i++) { ss += ($i - a)^2 } 

           $new = sqrt(ss/n)
           print
         }' inputfile

입력 행당 5개의 값에 평균을 더한 출력 예:

1       2       3       4       5       avg     sdev
23.3107 20.0372 21.7236 20.5328 21.2016 21.3611 1.13107

관련 정보