Straight bash, desde que você perguntou (embora note que estou usando matrizes associativas, exigindo o bash 4.0).
O truque está na expansão da sequência de chaves expressão {x..y}
que, para inteiros x any y, expande para o intervalo inclusivo de valores (isto é, [x, y]) como uma lista textual. Precisamos lançar um eval
também, já que a expansão de contraventamento acontece antes da expansão da variável.
declare -A data seen # explicit associative arrays
while read col range; do
data[$col]="${data[$col]} $(eval echo {${range/-/..}})"
done <<DATA
A 1-5
A 17-19
B 1-5
B 4-6
DATA
# dump array
#declare -p data
for ii in ${!data[@]}; do
seen=(); datum=""
# build list of unique values
for dd in ${data[$ii]}; do
(( ${seen[$dd]:-0} )) || datum="$datum $dd"
let seen[$dd]++
done
datum=${datum# } # drop leading space
datum=${datum// /,} # spaces to commas
printf "%-4s %s\n" "$ii" "$datum"
done
Uma variação na expansão da sequência é a{x..y}b
onde "a" é prefixada e "b" é anexado a cada termo da expansão: você pode usar isso para acrescentar um "," e alterar a variável de referência mexendo se desejar . A expansão de sequência processa incrementos de 1 ou -1 se x > y
Você também pode precisar ordenar a saída: iterar as chaves de um array associativo não tem uma ordem bem definida, e você não afirmou se os intervalos de entrada são pré-classificados (então eu não compliquei demais o código).