Введение
Bash поставляется с набором встроенных команд, которые можно использовать в командной строке или в сценариях оболочки.
В этой статье мы рассмотрим встроенную команду read
.
Интегрированное чтение Bash
read
— это встроенная команда bash, которая считывает строку из стандартного ввода (или файлового дескриптора) и разбивает строку на слова. Первое слово присваивается имени, второе — отчеству и так далее.
Общий синтаксис встроенной команды read
имеет следующий вид:
read [options] [name...]
Чтобы проиллюстрировать, как работает команда, откройте терминал, введите read var1 var2
и нажмите Invio
. Команда будет ждать, пока пользователь введет ввод. Введите два слова и нажмите Invio
.
read var1 var2
Слова присваиваются именам, передаваемым команде read
в качестве аргументов. Используйте echo
или printf
, чтобы проверить это:
echo $var1
echo $var2
Hello,
World!
Вместо того, чтобы печатать в терминале, вы можете передать стандартный ввод команде read
, используя другие методы, такие как конвейер, здесь-строка или здесьдок:
echo "Hello, World!" | (read var1 var2; echo -e "$var1 \n$var2")
read
и echo
заключаются в круглые скобки и выполняются в одной и той же подоболочке.
Hello,
World!
Вот пример использования строки здесь и printf
:
read -r var1 var2 <<< "Hello, World!"
Var1: Hello,
Var2: World!
Когда команде read
не заданы аргументы, вся строка присваивается переменной REPLY
:
echo "Hello, world!" | (read; echo "$REPLY")
Hello, World!
Если количество аргументов, переданных команде read
, больше, чем количество слов, считанных входом, оставшиеся слова присваиваются последнему имени:
echo "Linux is awesome." | (read var1 var2; echo -e "Var1: $var1 \nVar2: $var2")
Var1: Linux
Var2: is awesome.
В противном случае, если количество аргументов меньше количества имен, оставшимся именам присваивается пустое значение:
echo "Hello, World!" | (read var1 var2 var3; echo -e "Var1: $var1 \nVar2: $var2 \nVar3: $var3")
Var1: Hello,
Var2: World!
Var3:
По умолчанию read
интерпретирует обратную косую черту как escape-символ, что иногда может привести к неожиданному поведению. Чтобы отключить экранирование обратной косой черты, вызовите команду с параметром -r
.
Ниже приведен пример, показывающий, как работает команда read
при вызове с параметром -r
и без него:
read <<< "Hello, \tWorld!"
printf %s "$REPLY"
Hello, tWorld!
read -r <<< "Hello, \tWorld!"
printf %s "$REPLY"
Hello, \tWorld!
В общем, всегда следует использовать команду read
с параметром -r
.
Изменить разделитель
Поведение read
по умолчанию состоит в том, чтобы разбить строку на слова, используя один или несколько пробелов, табуляции и новой строки в качестве разделителей. Чтобы использовать другой символ в качестве разделителя, назначьте его переменной IFS
(внутренний разделитель полей).
echo "Linux:is:awesome." | (IFS=":" read -r var1 var2 var3; echo -e "$var1 \n$var2 \n$var3")
Linux
is
awesome.
Когда для IFS
задан символ, отличный от пробела или табуляции, слова разделяются ровно одним символом:
echo "Linux::is:awesome." | \
Строка разделена на четыре слова. Второе слово — это пустое значение, представляющее сегмент между разделителями. Он создан, потому что мы использовали два символа-разделителя рядом друг с другом ::
.
Var1: Linux
Var2:
Var3: is
Var4: awesome.
Вы можете использовать более одного разделителя для разделения строки. При указании нескольких разделителей назначайте символы переменной IFS
без пробела между ними.
Вот пример, который использует _
a -
в качестве разделителей:
echo 'Linux_is-awesome.' | (IFS="-_" read -r var1 var2 var3; echo -e "$var1 \n$var2 \n$var3")
Linux
is
awesome.
Строка подсказки
При написании интерактивных bash-скриптов вы можете использовать команду read
для получения пользовательского ввода.
Чтобы указать строку приглашения, используйте параметр -p
. Подсказка печатается перед выполнением read
и не включает новую строку.
Вот простой пример:
read -r -p "Are you sure?"
Как правило, вы должны использовать команду read
внутри цикла while
, чтобы заставить пользователя предоставить один из ожидаемых ответов.
Следующий код предложит пользователю перезагрузить систему:
while true; do
read -r -p "Do you wish to reboot the system? (Y/N): " answer
case $answer in
[Yy]* ) reboot; break;;
[Nn]* ) exit;;
* ) echo "Please answer Y or N.";;
esac
done
Если сценарий оболочки просит пользователей ввести конфиденциальную информацию, например пароли, используйте параметр -s
, который указывает команде read
не выводить ввод на терминал:
read -r -s -p "Enter your password: "
Назначьте слова матрице
Чтобы присвоить слова массиву вместо имен переменных, введите команду read
с параметром -a
:
read -r -a MY_ARR <<< "Linux is awesome."
for i in "${MY_ARR[@]}"; do
echo "$i"
done
Linux
is
awesome.
Когда указаны и массив, и имя переменной, все слова присваиваются массиву.
Вывод
Команда read
используется для разделения строки ввода на слова.