UNIX — универсальная среда программирования
Шрифт:
$
Если вы хотите узнать, как команда
pick
читает свои аргументы, запустите ее и нажмите клавишу RETURN после каждого приглашения. В том виде, в каком написана эта команда, она выполняется отлично: в цикле for i
аргументы обрабатываются правильно. Мы могли бы написать цикл другими способами: $ grep for pick
Выясните, что делает эта версия
for i in $*
$ pick '1 2' 3
1?
2?
3?
$
Эта
$*
: $ grep for pick
Попробуем другую версию
for i in "$*"
$ pick '1 2' 3
1 2 3?
$
Такая версия тоже не работает, поскольку "
$*
" является единым словом, которое образовано из всех аргументов, объединенных вместе с разделяющими пробелами. Но решение все-таки есть (это почти черная магия): строка трактуется особым образом интерпретатором и преобразуется в нужное число аргументов для командного файла: $ grep for pick
Попробуем третью версию
for i in "$@" '
$ pick '1 2' 3
1 2?
3?
$
Строка
$@
, не взятая в кавычки, идентична $*
; она обрабатывается иначе, только если заключена в кавычки. Мы использовали ее в команде overwrite
, чтобы сохранить аргументы для команды пользователя. В итоге мы можем сформулировать следующие правила:
$*
и $@
раскрываются как аргументы и снова распознаются; наличие пробелов в аргументах приводит к разбиению их на несколько аргументов; • "
$*
" является единым словом, которое образовано из всех аргументов командного файла, объединенных вместе с пробелами; • «
$*
» идентично аргументам, получаемым командным файлом: пробелы в аргументах игнорируются, в результате получается список слов, идентичных исходным аргументам. Если команда
pick
не имеет аргументов, она, по-видимому, должна читать стандартный входной поток, поэтому можно задать
$ pick < mailinglist
вместо
$ pick `cat mailinglist`
Но мы не будем исследовать эту версию команды
pick
во избежание некоторых неприятных осложнений. Кроме того, значительно проще написать такую же программу на Си. С ней вы познакомитесь в следующей главе. Первые два из приведенных ниже упражнений достаточно сложны, но полезны даже для опытных программистов, работающих на языке
shell
. Упражнение 5.24
Попробуйте написать программу
pick
, которая читает аргументы из стандартного входного потока, если ничего не задано в командной строке. Она должна правильно обрабатывать пробелы. Будет ли допустим ответ q
? Если нет, то попытайтесь выполнить следующее упражнение. Упражнение 5.25
Хотя встроенные команды интерпретатора, такие, как
read
и set
, нельзя переключить,
sh(1)
, в котором описывается команда exec
, и придумайте, как читать из /dev/tty
без вызова порожденного интерпретатора. (Может оказаться полезным сначала прочитать гл. 7.) Упражнение 5.26
(Более простое.) Используйте команду
read
в вашем файле .profile
для инициации TERM
, а также всего, что зависит от нее, например позиции табуляции. 5.8 Команда
news
: служба информации пользователей В гл. 1 упоминалось о том, что в вашей системе может быть команда
news
для передачи сообщений, представляющих интерес для всех пользователей системы. Хотя названия команды и ее детали могут различаться, большинство систем имеет службу информации. Мы рассматриваем команду news
не для замены вашей местной команды, а чтобы показать, как легко написать такую программу на языке shell
. Неплохо было бы сравнить реализацию предлагаемой здесь команды news с вашей версией. Обычно основная идея таких программ заключается в том, что отдельные фрагменты новостей хранятся по одному в файлах в специальном каталоге типа
/usr/news
. Наша команда news
сравнивает время изменения файлов в каталоге /usr/news
и вашем исходном каталоге (.news_time
). В целях отладки мы можем использовать каталог '.'
как для файлов новостей, так и для news_time
. Можно заменить его на /usr/news
, когда программа будет готова для общего пользования:
$ cat news
# news: print news files, version 1
HOME=. # debugging only
cd . # place holder for /usr/news
for i in `ls -t * $HOME/.news_time`
do
case $i in
*/.news_time) break ;;
*) echo news: $i
esac
done
touch $HOME/.news_time
$ touch .news-time
$ touch x
$ touch y
$ news
news: y
news: x
$
Команда
touch
заменяет время последней модификации файла, заданного в качестве аргумента, на настоящее время, не подвергая сам файл модификации. Для отладки мы даем только эхо имен файлов новостей, а не печатаем их. Цикл завершается при обнаружении news_time
, тем самым перечисляются только файлы со свежими новостями. Заметьте, что символ *
в операторе case
может быть сопоставлен с /
, что недопустимо для шаблонов имен файлов. А что будет, если news_time
не существует?
Поделиться:
Популярные книги
Блуждающие огни 4
4. Блуждающие огни
Фантастика:
попаданцы
альтернативная история
5.00
рейтинг книги
Я сделаю это сама
1. Магический XVIII век
Любовные романы:
любовно-фантастические романы
5.00
рейтинг книги
Флеш Рояль
Детективы:
триллеры
7.11
рейтинг книги
Боярышня Дуняша
1. Боярышня
Фантастика:
попаданцы
альтернативная история
5.00
рейтинг книги
Газлайтер. Том 8
8. История Телепата
Фантастика:
попаданцы
альтернативная история
аниме
5.00
рейтинг книги
Леди для короля. Оборотная сторона короны
3. Королевская охота
Любовные романы:
любовно-фантастические романы
5.00
рейтинг книги
На границе империй. Том 10. Часть 1
Вселенная EVE Online
Фантастика:
космическая фантастика
попаданцы
5.00
рейтинг книги
Черный Маг Императора 5
5. Черный маг императора
Фантастика:
юмористическое фэнтези
попаданцы
аниме
5.00
рейтинг книги
Невест так много. Дилогия
Невест так много
Любовные романы:
любовно-фантастические романы
7.62
рейтинг книги
Идеальный мир для Социопата 3
3. Социопат
Фантастика:
боевая фантастика
6.17
рейтинг книги
Повелитель механического легиона. Том VIII
8. Повелитель механического легиона
Фантастика:
технофэнтези
аниме
фэнтези
5.00
рейтинг книги
Наследник павшего дома. Том I
1. Расколотый мир
Фантастика:
фэнтези
попаданцы
аниме
5.00
рейтинг книги
Крещение огнем
5. Ведьмак
Фантастика:
фэнтези
9.40
рейтинг книги
Камень Книга двенадцатая
12. Камень
Фантастика:
боевая фантастика
городское фэнтези
аниме
фэнтези
5.00