문자열로 구분된 부분으로 파일을 정렬하고 싶지만 awk에서 처리하기에는 더 큰 부분입니다.
구분 기호 사이에 행을 저장한 다음 asort를 사용하여 정렬할 수 있다는 내용을 읽었지만 두 번째 열을 사용하여 정렬해야 합니다.
구분 기호 사이의 출력을 변수(케이) 그런 다음 변수 값을 명령에 파이프합니다.|, 마지막으로 출력을 읽고 처리한 후 인쇄합니다.
그러나print variable|"sort -k2,2"|getline v
줄을 서다(?) 막혔어요.
명령을 실행할 수 있어요더 추악한함수를 사용하는 방법을 사용했지만 system()
명령에 변수를 전달하려면 echo를 사용해야 한다고 생각했고 출력은 변수 v에 저장되지 않고 오류 코드에 저장되었습니다.
$ awk 'BEGIN{ cmd="sort -k2,2"; k="1\tB\n2\tA"; v=system("echo \""k"\" | "cmd); print "OK: "v}'
2 A
1 B
OK: 0
이것더 나은print k|command
(removing ) 을 사용하여 명령을 실행 |getline v
하지만 print "OK"
하위 명령이 출력되기 전에 완료됩니다. 출력은 변수에 저장되지 않습니다.V.
$ awk 'BEGIN{ cmd="sort -k2,2"; k="1\tB\n2\tA"; print k|cmd; print "OK: "v}'
OK:
2 A
1 B
명령 출력을 변수에 저장하려면 어떻게 해야 합니까? 아니면 적어도 계속하기 전에 이전 하위 명령이 완료될 때까지 기다릴 수 있습니까?
답변1
이것이 당신이 원하는 것입니까(GNU awk를 사용하여공동 프로세스)?
$ cat tst.awk
BEGIN {
cmd = "sort -k2,2"
k = "1\tB\n2\tA"
print k |& cmd
close(cmd, "to")
while ((cmd |& getline line) > 0) {
v = v line ORS
}
close(cmd)
print "OK:"
printf "%s", v
}
$ awk -f tst.awk
OK:
2 A
1 B
위에서 GNU awk가 사용되었기 때문에(그리고 이미 언급하셨습니다)분류()귀하의 질문에 이것은 gawk에만 해당됩니다. gawk에는 이미 정렬 기능이 내장되어 있으므로 이 작업을 수행할 필요가 없을 것입니다.다음으로 정렬sort
위와 같이 각 호출에 대해 하위 쉘을 생성하는 대신:
$ cat tst.awk
BEGIN {
k = "1\tB\n2\tA"
split(k,lines,/\n/)
for (i in lines) {
lines[i] = gensub(/[^\t]*\t([^\t]+)/,"\\1\t&",1,lines[i])
}
PROCINFO["sorted_in"] = "@val_str_asc"
for (i in lines) {
v = v gensub(/[^\t]\t/,"",1,lines[i]) ORS
}
print "OK:"
printf "%s", v
}
$ awk -f tst.awk
OK:
2 A
1 B
하지만 내 생각에 이것은 수행하려고 하는 더 어려운 작업 중 일부의 단순화된 버전이며 실제로는 보조 프로세스가 필요합니다.
답변2
이 글에 설명된 문제에 대한 해결책에 관심이 있는 사람논평:
awk는 다른 명령(예: squeue)의 출력을 처리하고 있으며 다른 사용자의 작업에 대한 완전한 정보가 필요하지 않으며 이를 축소하고 싶지만 제출된 작업이 언제인지 알 수 있도록 여전히 올바른 위치에 보관해야 합니다. 달리는 동안 참가할 수 있습니다.
alias squeue="_squeue() {
/usr/bin/squeue --format=\"%.8i %.9P %.20j %.10u %.2t %.10M %.10L %.6D %R\" \$@ \
| awk '
BEGIN { cmd=\"sort -k2,2 -k5,5 -k4,4\" }
function sort(buf) {
sorted=\"\"
gsub(\"^\"ORS\"*|\"ORS\"{2,}|\"ORS\"*$\", \"\", buf)
if (length(buf)>0) {
print buf |& cmd
close(cmd, \"to\")
while ((cmd |& getline line) > 0) {
sorted = sorted line ORS
}
close(cmd)
}
return sorted
}
NR <= 1 { print; next }
/'\$USER'/ {
printf(\"%s\", sort(buf))
buf=\"\"
print
partition=\$2; user=\$4; st=\$5;
next
}
{ buf = buf ORS \$0 }
END {
printf(\"%s\", sort(buf))
}
' \
| awk '
BEGIN { partition=\"\"; user=\"\"; st=\"\"; c=0; n=0; }
function print_count() {
if(c>0) { print \" (count: \"c\" jobs, \"n\" nodes)\"; c=0; n=0; }
}
NR <= 1 { print \$0; next }
/'\$USER'/ {
print_count()
print;
next
}
\$2!=partition || \$4!=user || \$5!=st {
print_count()
printf(\"%-98s\", substr(\$0,0, 98));
partition=\$2; user=\$4; st=\$5;
}
{ n+=\$8; c++ }
END {
print_count()
}' \
| sed '/(count: .*)$/{s/.*/\x1b[90m&\x1b[0m/p;d};
/\s'\$USER'\s\+[^R]\+\s/{s/.*/\x1b[1m&\x1b[0m/p;d}'
}
_squeue"