Как читать переменное количество переменных в bash

Если ваш скрипт/функция принимает числа из командной строки, вам не нужно читать их с помощью read(, который считывается со стандартного ввода ).

Вместо:

addition () {
    sum=0

    for number do
        sum=$(( sum + number ))
    done

    printf 'Sum is %d\n' "$sum"
}

Цикл также может быть записан более явно как

for number in "$@"; do
    sum=$(( sum + number ))
done

В обоих вариантах цикла переменной numberбудет присвоено значение каждого позиционного параметра («аргумент командной строки» )по очереди, и тело цикла добавит их к sumпеременная.

Обратите внимание, что приведенный выше код предполагает, что все аргументы командной строки являются целыми числами, без проверки того, что они таковы.


Для расширенного вывода:

addition () {
    sum=0

    for number do
        sum=$(( sum + number ))
    done

    ( IFS='+'; printf '%s = %d\n' "$*" "$sum" )
}

"$*"будет расширен до одной строки, состоящей из позиционных параметров, соединенных с первым символом $IFSв качестве разделителя.

Тестирование:

$ addition 1 2 3 90 32
1+2+3+90+32 = 128
2
08.06.2021, 16:03
1 ответ

Помимо различных способов улучшения ввода данных, как показано в другом ответе, небольшое изменение заставит ваш скрипт работать, как задумано.

В строке

echo $names[${i}]

оболочка расширится $namesи ${i}, что, вероятно, приведет к

[1]
[2]

и т. д., при условии, что namesне определено. В противном случае перед открывающими скобками будет добавлено значение names.
(Как упоминалось в комментарии Stéphane Chazelas , результирующий файл [1]и т. д. может быть заменен соответствующими именами файлов 1и т. д. из-за отсутствия кавычек, если такие файлы существуют.)

Вместо этого используйте

echo "${names[${i}]}"

Редактировать:

Как сказано в комментарии ilkkachu , в сценарии из вопроса достаточно использовать

echo "${names[i]}"

, так как индекс представляет собой арифметическое расширение, и вам не нужно $при ссылке на переменные.

2
28.07.2021, 11:26

Теги

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