KnigaRead.com/
KnigaRead.com » Компьютеры и Интернет » Программирование » Мендель Купер - Искусство программирования на языке сценариев командной оболочки

Мендель Купер - Искусство программирования на языке сценариев командной оболочки

На нашем сайте KnigaRead.com Вы можете абсолютно бесплатно читать книгу онлайн "Мендель Купер - Искусство программирования на языке сценариев командной оболочки". Жанр: Программирование издательство неизвестно, год неизвестен.
Перейти на страницу:

#

# Этот модифицированный вариант включен в документ на основе

#+ документа "LICENSE" из пакета "Crack"

#+ с которым распространяется оригинальный сценарий.


# Этот скрипт обрабатывает текстовые файлы и создает отсортированный список

#+ слов, найденных в этих файлах.

# Он может оказаться полезным для сборки словарей

#+ и проведения лексикографического анализа.


E_BADARGS=65


if [ ! -r "$1" ] # Необходим хотя бы один аргумент --

then #+ имя файла.

echo "Порядок использования: $0 имена_файлов"

exit $E_BADARGS

fi


# SORT="sort" # Необходимость задания ключей сортировки отпала.

#+ Изменено, по отношению к оригинальному сценарию.


cat $* | # Выдать содержимое файлов на stdout.

tr A-Z a-z | # Преобразовать в нижний регистр.

tr ' ' '12' | # Новое: заменить пробелы символами перевода строки.

# tr -cd '12[a-z][0-9]' | # В оригинальном сценарии: удалить все символы,

#+ которые не являются буквами или цифрами.

tr -c '12a-z' '12' | # Вместо удаления

#+ неалфавитно-цифровые символы заменяются на перевод строки.

sort |

uniq | # Удалить повторяющиеся слова.

grep -v '^#' | # Удалить строки, начинающиеся с "#".

grep -v '^$' # Удалить пустые строки.


exit 0

Пример A-10. Расчет индекса "созвучности"

#!/bin/bash

# soundex.sh: Расчет индекса "созвучности"


# =======================================================

# Сценарий Soundex

# Автор

# Mendel Cooper

# [email protected]

# 23 Января 2002 г.

#

# Условия распространения: Public Domain.

#

# Несколько отличающаяся версия этого сценария была опубликована

#+ Эдом Шэфером (Ed Schaefer) в Июле 2002 года в колонке "Shell Corner"

#+ "Unix Review" on-line,

#+ http://www.unixreview.com/documents/uni1026336632258/

# =======================================================


ARGCOUNT=1 # Требуется аргумент командной строки.

E_WRONGARGS=70


if [ $# -ne "$ARGCOUNT" ]

then

echo "Порядок использования: `basename $0` имя"

exit $E_WRONGARGS

fi


assign_value () # Присвоить числовые значения

{ #+ символам в имени.


val1=bfpv # 'b,f,p,v' = 1

val2=cgjkqsxz # 'c,g,j,k,q,s,x,z' = 2

val3=dt # и т.п.

val4=l

val5=mn

val6=r


# Попробуйте разобраться в том, что здесь происходит.


value=$( echo "$1"

| tr -d wh

| tr $val1 1 | tr $val2 2 | tr $val3 3

| tr $val4 4 | tr $val5 5 | tr $val6 6

| tr -s 123456

| tr -d aeiouy )


# Символам в имени присваиваются числовые значения.

# Удаляются повторяющиеся числа, если они не разделены гласными.

# Гласные игнорируются, если они не являются разделителями, которые удаляются в последнюю очередь.

# Символы 'w' и 'h' удаляются в первую очередь.

}


input_name="$1"

echo

echo "Имя = $input_name"


# Перевести все символы в имени в нижний регистр.

# ------------------------------------------------

name=$( echo $input_name | tr A-Z a-z )

# ------------------------------------------------


# Начальный символ в индекса "созвучия": первая буква в имени.

# --------------------------------------------


char_pos=0 # Начальная позиция в имени.

prefix0=${name:$char_pos:1}

prefix=`echo $prefix0 | tr a-z A-Z`

# Первую букву в имени -- в верхний регистр.


let "char_pos += 1" # Передвинуть "указатель" на один символ.

name1=${name:$char_pos}


# ++++++++++++++++++++++++++++ Исключение отдельных ситуаций +++++++++++++++++++++++++++++++

# Теперь мы передвинулись на один символ вправо.

# Если второй символ в имени совпадает с первым

#+ то его нужно отбросить.

# Кроме того, мы должны проверить -- не является ли первый символ

#+ гласной, 'w' или 'h'.


char1=`echo $prefix | tr A-Z a-z` # Первый символ -- в нижний регистр.


assign_value $name

s1=$value

assign_value $name1

s2=$value

assign_value $char1

s3=$value

s3=9$s3 # Если первый символ в имени -- гласная буква

#+ или 'w' или 'h',

#+ то ее "значение" нужно отбросить.

#+ Поэтому ставим 9, или другое

#+ неиспользуемое значение, которое можно будет проверить.


if [[ "$s1" -ne "$s2" || "$s3" -eq 9 ]]

then

suffix=$s2

else

suffix=${s2:$char_pos}

fi

# ++++++++++++++++++++++++ Конец исключения отдельных ситуаций +++++++++++++++++++++++++++++++


padding=000 # Дополнить тремя нулями.


soun=$prefix$suffix$padding # Нули добавить в конец получившегося индекса.


MAXLEN=4 # Ограничить длину индекса 4-мя символами.

soundex=${soun:0:$MAXLEN}


echo "Индекс созвучия = $soundex"


echo


# Индекс "созвучия" - это метод индексации и классификации имен

#+ по подобию звучания.

# Индекс "созвучия" начинается с первого символа в имени,

#+ за которым следуют 3-значный расчетный код.

# Имена, которые произносятся примерно одинаково, имеют близкие индексы "созвучия".


# Например:

# Smith и Smythe -- оба имеют индекс "созвучия" "S530".

# Harrison = H625

# Hargison = H622

# Harriman = H655


# Как правило эта методика дает неплохой результат, но имеются и аномалии.

#

#

# Дополнительную информацию вы найдете на

#+ "National Archives and Records Administration home page",

#+ http://www.nara.gov/genealogy/soundex/soundex.html


# Упражнение:

# ----------

# Упростите блок "Исключение отдельных ситуаций" .


exit 0

Пример A-11. "Игра "Жизнь""

#!/bin/bash

# life.sh: Игра "Жизнь"


# ##################################################################### #

# Это Bash-версия известной игры Джона Конвея (John Conway) "Жизнь". #

# --------------------------------------------------------------------- #

# Прямоугольное игровое поле разбито на ячейки, в каждой ячейке может #

#+ располагаться живая особь. #

# Соответственно, ячейка с живой особью отмечается точкой, #

#+ не занятая ячейка -- остается пустой. #

# Изначально, ячейки заполняются из файла -- #

#+ это первое поколение, или "поколение 0" #

# Воспроизводство особей, в каждом последующем поколении, #

#+ определяется следующими правилами #

# 1) Каждая ячейка имеет "соседей" #

#+ слева, справа, сверху, снизу и 4 по диагоналям. #

# 123 #

# 4*5 #

# 678 #

# #

# 2) Если живая особь имеет 2 или 3 живых соседей, то она остается жить.#

# 3) Если пустая ячейка имеет 3 живых соседей -- #

#+ в ней "рождается" новая особь #

SURVIVE=2 #

BIRTH=3 #

# 4) В любом другом случае, живая особь "погибает" #

# ##################################################################### #


startfile=gen0 # Начальное поколение из файла по-умолчанию -- "gen0".

# если не задан другой файл, из командной строки.

#

if [ -n "$1" ] # Проверить аргумент командной строки -- файл с "поколениемn 0".

then

if [ -e "$1" ] # Проверка наличия файла.

then

startfile="$1"

fi

fi


ALIVE1=.

DEAD1=_

# Представление "живых" особей и пустых ячеек в файле с "поколением 0".


# Этот сценарий работает с игровым полем 10 x 10 grid (может быть увеличено,

#+ но большое игровое поле будет обрабатываться очень медленно).

ROWS=10

COLS=10


GENERATIONS=10 # Максимальное число поколений.


NONE_ALIVE=80 # Код завершения на случай,

#+ если не осталось ни одной "живой" особи.

TRUE=0

FALSE=1

ALIVE=0

DEAD=1


avar= # Текущее поколение.

generation=0 # Инициализация счетчика поколений.


# =================================================================


let "cells = $ROWS * $COLS"

# Количество ячеек на игровом поле.


declare -a initial # Массивы ячеек.

declare -a current


display ()

{


alive=0 # Количество "живых" особей.

# Изначально -- ноль.


declare -a arr

arr=( `echo "$1"` ) # Преобразовать аргумент в массив.


element_count=${#arr[*]}


local i

local rowcheck


for ((i=0; i<$element_count; i++))

do


# Символ перевода строки -- в конец каждой строки.

let "rowcheck = $i % ROWS"

if [ "$rowcheck" -eq 0 ]

then

echo # Перевод строки.

echo -n " " # Выравнивание.

fi


cell=${arr[i]}


if [ "$cell" = . ]

then

let "alive += 1"

fi


echo -n "$cell" | sed -e 's/_/ /g'

# Вывести массив, по пути заменяя символы подчеркивания на пробелы.

done


return


}


IsValid () # Проверка корректности координат ячейки.

{


if [ -z "$1" -o -z "$2" ] # Проверка наличия входных аргументов.

then

return $FALSE

fi


local row

local lower_limit=0 # Запрет на отрицательные координаты.

local upper_limit

local left

local right


let "upper_limit = $ROWS * $COLS - 1" # Номер последней ячейки на игровом поле.

Перейти на страницу:
Прокомментировать
Подтвердите что вы не робот:*