суммируйте пару столбцов на основе соответствия полям

Это кажется очень похожим на недавний вопрос.

https://stackoverflow.com/questions/11596059/how-do-i-read-any-one-key-in-bash/11596145#11596145

read -n 1 x; while read -n 1 -t .1 y; do x="$x$y"; done

Но, как упомянуто в том потоке, с помощью диалогового окна или подобных сценариев menuing программы был бы более оптимальный вариант.

Или... Вы желаете отправить те нажатия клавиш в программу? Если так, Вы, вероятно, хотите использовать, ожидают.

11
06.04.2019, 04:37
4 ответа

Я бы сделал это в Perl:

$ perl -lane '$k{"$F[0] $F[1]"}+=$F[2]+$F[3]; 
              END{print "$_ $k{$_}" for keys(%k) }' file 
2 1019 15
2 1021 4
2 1030 6
2 1031 8
2 1022 9

или awk:

awk '{a[$1" "$2]+=$3+$4}END{for (i in a){print i,a[i]}}' file 

Если вы хотите, чтобы вывод отсортирован в соответствии со втором столбцом, вы могли бы просто трусить в сортировка :

awk '{a[$1" "$2]+=$3+$4}END{for (i in a){print i,a[i]}}' file | sort -k2

Обратите внимание, что оба решения Включите 1-й столбец также. Идея состоит в том, чтобы использовать первые и второе столбцы в качестве клавиш к хеш (в Perl) или ассоциативном массиве (в awk). Ключ в каждом решении Column1 Column1 Column2 Итак, если две линии имеют один и тот же столбец два, но другой столбец один, они будут сгруппированы отдельно:

$ cat file
2 1019 2 3
2 1019 4 1
3 1019 2 2

$ awk '{a[$1" "$2]+=$3+$4}END{for (i in a){print i,a[i]}}' file
3 1019 4
2 1019 10
12
27.01.2020, 19:57

Может быть, это может помочь, но это столбец 1 всегда 2, а результаты зависят от него?

awk '{ map[$2] += $3 + $4; } END { for (i in map) { print "2", i, map[i] | "sort -t't'" } }' file

или как упомянуто Glenn Jackman в комментариях о сортировке:

gawk '{ map[$2] += $3 + $4; } END { PROCINFO["sorted_in"] = "@ind_str_asc"; for (i in map) { print 2, i, map[i] } }' file
]
7
27.01.2020, 19:57

Вы могли бы предварительно отсортировать данные и дать awk обрабатывать детали:

sort -n infile | awk 'NR>1 && p!=$2 {print p,s} {s+=$3+$4} {p=$2}'

Вы можете сбросить аккумулятор:

sort -n infile | awk 'NR>1 && p!=$2 {print p,s;s=0} {s+=$3+$4} {p=$2}'

Вывод:

1019 15
1021 19
1022 28
1030 34

Если вы действительно хотите, чтобы держать первый столбец, сделайте что-то подобное :

sort -n infile | awk 'NR>1 && p!=$1FS$2 {print p,s} {s+=$3+$4} {p=$1FS$2}'

Выход:

2 1019 15
2 1021 19
2 1022 28
2 1030 34

Объяснение

Переменная P Удерживает значение $ 2 значение предыдущей строки, или $ 1FS $ 2 во втором случай выше. Это означает, что {Print P, S} срабатывает, когда $ 2 предыдущей строки не совпадает с одним на текущей строке ( P! = $ 2 ).

4
27.01.2020, 19:57

Uso de la navaja suiza utilmlr:

mlr --nidx   put '$5=$3+$4'   then   stats1 -g 1,2 -f 5 -a sum   infile

Salida:

2   1019    15
2   1021    4
2   1022    9
2   1030    6
2   1031    8

Notas:

  • --nidxle dice a mlrque use nombres de campos numéricos.

  • put '$5=$3+$4'crea un nuevo campo 5th , la suma de los campos 3 y 4 .

  • La función stats1(o " verbo " )es una navaja suiza más pequeña
    dentro de la mayor navaja suiza de mlr, con varios funciones basadas en acumuladores como sum, count, mean, , etc.

    stats1 -g 1,2agrupa los datos por columnas 1 y 2 , y -f 5 -a sumluego suma el campo de esos grupos 5 . stats1imprime solo campos con nombre.

2
27.01.2020, 19:57

Теги

Похожие вопросы