Несмотря на то что команда eval еще не обсуждалась, можно воспользоваться ею, если требуется уточнить последний параметр командной строки (обычно в качестве этого параметра используется имя файла). Получить последний параметр командной строки вы можете двумя способами. Во–neрвых, с помощью команды eval echo \$$#, а во–вторых, путем применения команды shift `expr $# - 2`.
20.1.3. Преобразования файла с помощью команды shift
Использование возможностей команды shift значительно облегчает работу с опциями командной строки. Рассмотрим сценарий, выполняющий преобразование регистра символов. При этом будет применяться команда tr.
При выполнении сценария используются две опции:
-l для нижнего регистра -u для верхнего регистра
С помощью команды shift можно запустить на выполнение сценарий, работающий с опциями -l и -u. Ниже приводится первый вариант этого сценария.
$ pg tr_case
#!/bin/sh
#tr_case
#преобразование регистра usage ()
{
# сообщение usage
echo "usage:`basename $0` -[l|u] file [files]" >&2
exit 1
}
if [ $# -eq 0 ]; then
# параметры не переданы!
usage
fi
while [ $# -gt 0 ]
do
case $1 in
-u|-U) echo " -uoption specified"
# здесь укажите все установки переменных для нижнего регистра, затем
# примените команду shift shift
;;
-l|-L) echo " -l option specified"
# здесь укажите все установки переменных для верхнего регистра, затем
# примените команду shift shift
;;
*) usage
;;
esac
done
Вначале выполняется проверка, имеются ли аргументы в сценарии. Если они отсутствуют, выводится сообщение usage. При обработке аргументов с помощью конструкции case отображается значение каждой передаваемой опции. После этого применяется команда shift, выполняющая вывод в командной строке очередной опции. Если все опции обработаны, отображается сообщение usage.
А теперь посмотрим, как выглядят выводимые результаты при передаче сценарию двух некорректных аргументов.
$ tr_case -u -l -к
— и option specified
-l option specified
usage: tr_case —[l|u] file [files]
На следующем этапе обрабатываются файлы, передающиеся после обработки опций с помощью конструкции case. Для реализации этой задачи достаточно выполнить небольшие изменения. В конструкции case шаблон * заменяется шаблоном -*, что позволяет передавать некорректные опции, например -p или -q.
Чтобы с помощью цикла for обрабатывать каждый файл, следует для всех передаваемых имен файлов указывать шаблон *. Кроме того, с помощью опции -f проверяется наличие всех требуемых имен файлов.
Итак, улучшенный вариант конструкции case имеет следующий вид:
case
...
-*) usage
*) if [ -f $1 ]; then
FILES=$FILES" "$1 # присвоить переменной имена файлов
else
echo "`basename $0` cannot find the file $1"
fi
shift # получите следующий параметр !
esac
Следует также задать значения некоторых переменных в зависимости от указанной опции (-1, — u). При этом используются следующие переменные:
| TRCASE | Указывает тип преобразования регистра (верхний или нижний регистр) |
| ЕХТ | Все преобразованные файлы имеют либо расширение .UC (для верхнего регистра), либо расширение .LC (для нижнего регистра). В исходный файл изменения не вносятся |
| OPT | При передаче опций принимает значение yes, в противном случае — no. Только тогда, когда опции не передаются, можно перехватить их значение и вывести на экран сообщение |
Для выполнения реального преобразования достаточно добавить еще один фрагмент кода, включающий команду tr. Этот фрагмент кода добавляется в конец сценария. При этом для считывания имен файлов используется цикл for и конструкция case. Ниже приводится код созданного сценария:
$ pg tr_case
#!/bin/sh
#tr_case
#преобразование символов файлов либо в верхний, либо в нижний регистр
FILES=""
TRCASE=""
EXT=""
OPT=no
# вызывается при неудачном преобразовании
error_msg ()
{
_FILENAME=$1
echo "`basename $0`: Error the conversion failed on $_FILENAME"
}
if [ $# -eq 0 ] then
echo "For more info try `basename $0` —help"
exit 1
fi
while [ $# -gt 0 ]
do
case $1 in
# установите переменные на базе применяемой опции
-u)
TRCASE=upper
ЕХТ=".UС"
OPT=yes
shift
;;
-l)