| У Вас ошибка в курсе |
Оболочка bash
Перенаправление ввода/вывода, каналы и фильтры
Хотя обычно, как было сказано, ввод/вывод программы связаны со стандартными потоками, в оболочке существуют специальные средства для перенаправления ввода/вывода.
Операторы >, < и >>
Для обозначения перенаправления используются символы ">", "<" и ">>". Чаще всего используется перенаправление вывода команды в файл. Вот соответствующий пример:
[user]$ ls -l > /home/jim/dir.txt
По этой команде в файле /home/jim/dir.txt будет сохранен перечень файлов и подкаталогов того каталога, который был текущим на момент выполнения команды ls ; при этом если указанного файла не существовало, то он будет создан; если он существовал, то будет перезаписан; если же вы хотите, чтобы вывод команды был дописан в конец существующего файла, то надо вместо символа > использовать >>. При этом наличие пробелов до или после символов > или >> несущественно и служит только для удобства пользователя.
Вы можете направить вывод не только в файл, но и на вход другой команды или на устройство (например, принтер). Так, для подсчета числа слов в файле /home/jim/report.txt можно использовать следующую команду:
[user]$ cat /home/jim/report.txt | wc -w
а для вывода файла на печать - команду:
[user]$ cat /home/jim/report.txt > lpr
Как видите, оператор > служит для перенаправления выходного потока. По отношению к входному потоку аналогичную функцию выполняет оператор <. Приведенный выше пример команды для подсчета числа слов в определенном файле можно переписать следующим образом (обратите внимание на отсутствие команды cat ):
[user]$ wc -w < /home/jim/report.txt
Этот вариант перенаправления часто используется в различных скриптах, применительно к тем командам, которые обычно воспринимают ввод (или ожидают ввода) с клавиатуры. В скрипте же, автоматизирующем какие-то рутинные операции, можно дать команде необходимую информацию из файла, в который заранее записано то, что нужно ввести для выполнения этой команды.
В силу того, что символы <, > и >> действуют на стандартные потоки, их можно использовать не только тем привычным образом, как это делается обычно, но и несколько по-другому. Так, следующие команды эквивалентны:
[user]$ cat > file [user]$ cat>file [user]$ >file cat [user]$ > file cat
Однако сам по себе (без какой-либо команды, для которой определены стандартные потоки) символ перенаправления не может использоваться, так что нельзя, например, введя в командной строке
[user]$ file1 > file2
получить копию какого-то файла. Но это не уменьшает значения данного механизма, ведь стандартные потоки определены для любой команды. При этом перенаправить можно не только стандартный ввод и вывод, но и другие потоки. Для этого надо указать перед символом перенаправления номер перенаправляемого потока. Стандартный ввод stdin имеет номер 0, стандартный вывод stdout - номер 1, стандартный поток сообщений об ошибках stderr - номер 2. То есть полный формат команды перенаправления имеет вид (напомним, что пробелы возле > не обязательны):
command N > M
где N и M - номера стандартных потоков (0,1,2) или имена файлов. Употребление в некоторых случаях символов <, > и >> без указания номера канала или имени файла возможно только потому, что вместо отсутствующего номера по умолчанию подставляется 1, т. е. стандартный вывод. Так, оператор > без указания номера интерпретируется как 1 >.
Кроме простого перенаправления стандартных потоков существует еще возможность не просто перенаправить поток в тот или иной канал, а сделать копию содержимого стандартного потока. Для этого служит специальный символ &, который ставится перед номером канала, на который перенаправляется поток:
command N > &M
Такая команда означает, что выход канала с номером N направляется как на стандартный вывод, так и дублируется в канал с номером M. Например, для того, чтобы сообщения об ошибках дублировались на стандартный вывод, надо дать команду 2>&1, в то время как 1>&2 дублирует stdout в stderr. Такая возможность особенно полезна при перенаправлении вывода в файл, так как мы тогда одновременно и видим сообщения на экране, и сохраняем их в файле.