Чтение онлайн

на главную - закладки

Жанры

UNIX — универсальная среда программирования
Шрифт:

printf "double %s, file %s, line %d\n", $i, FILENAME, NR

 if (NF > 0)

lastword = $NF

}' $*

*

$

Операция

++
означает автоувеличение операнда, а операция
– -
— его автоуменьшение.

Встроенная переменная

FILENAME
хранит имя текущего входного файла. Поскольку в переменной
NR
подсчитывается число строк с начала входного потока, мы изменяем ее значение всякий раз при изменении имени файла, чтобы точно указать строку с двойником.

Оператор

if
— такой же, как в языке Си:

if (условие)

 оператор1

else

 оператор2

Если

условие верно, то выполняется
оператор1
; если оно ложно и если альтернативная часть присутствует, то выполняется
оператор2
. Альтернативная часть не обязательна.

Цикл

for
аналогичен таковому в языке Си, но отличается от цикла в языке
shell
:

for (выражение1; условие; выражение2)

 оператор

Цикл

for
идентичен приведенному ниже оператору, который также допустим в программе
awk
:

Выражение1 while (условие) {

 оператор

 выражение2

}

Например, конструкция

for (i=2; i <= NF; i++)

является циклом с

i
, принимающим значения 2, 3 и т.д., включая число полей
NF
.

Оператор

break
вызывает немедленный выход из цикла
while
или
for
; оператор
continue
инициирует переход к следующему шагу цикла (к условию в операторе
while
или к
выражению2
в операторе
for
). Оператор
next
вызывает чтение следующей входной строки и сопоставление ее с шаблонами с начала программы
awk
, а оператор
exit
— немедленный переход на действия, определенные в шаблоне
END
.

Массивы

Как и в большинстве языков программирования, в

awk
есть массивы. В качестве простого примера приведем программу
awk
, в которой каждая входная строка заносится в отдельный элемент массива, индексируемого номером строки, а затем они печатаются в обратном порядке:

$ cat backwards

# backwards: print input in backward line order

awk ' { line[NR] = $0 }

END { for (i = NR; i > 0; i--) print line[i] } ' $*

$

Заметьте, что подобно переменным, массивы не нужно описывать; размер массива ограничен только объемом памяти, доступным на вашей машине. Конечно, если очень большой файл заносится в массив, в конце концов, это может привести к исчерпанию ресурсов памяти. Для печати конца большого файла в обратном порядке следует обратиться за помощью к команде

tail
:

$ tail -5 /usr/dict/web2 | backwards

zymurgy

zymotically

zymotic

zymosthenic

zymosis

$

Команда

tail
использует возможности файловой системы — операцию "поиск" (seeking), позволяющую перейти к концу файла без чтения всей предшествующей информации. Подробнее эта операция будет рассмотрена при обсуждении функции
lseek
в гл. 7. (В нашей команде
tail
есть флаг
– r
, который определяет печать строк в обратном порядке, заменяя команду
backwards
).

При обычной обработке входная строка разбивается на поля. Эту операцию можно выполнить с помощью встроенной функции

split
над любой строкой:

n = split(s, arr, sep)

Строка

s
разбивается на поля, записываемые в элементы массива
arr
от 1 до
n
. Используется символ разделения полей
sep
, если он задан; в противном случае применяется текущее значение переменной
FS
. Например, обращение
split($0, а, ":")
разбивает входную строку на столбцы, что подходит для обработки файла
/etc/passwd
, поэтому обращение
split("9/29/83", date, "/")
разбивает дату по символам дробной черты.

$ sed 1q /etc/passwd | awk '{split($0, a, ":"); print a[1]}'

root

$ echo 9/29/83 | awk '{split($0, date, "/"); print date[3]}'

83

$

В табл. 4.5 перечислены встроенные функции

awk
.

cos(expr)
Косинус
expr
exp(expr)
Возведение в степень
expr
getline
Чтение следующей входной строки; возвращает 0 в случае конца файла, в противном случае 1
index(s1, s2)
Положение строки
s2
в
s1
; возвращает 0, если строка не входит
int(expr)
Целая часть
expr
; округляет по минимуму
length(s)
Длина строки
s
log(expr)
Натуральный логарифм
expr
sin(expr)
Синус
expr
split(s, a, c)
Разбиение
s
на
а[1]
...
a[n]
по символу
c
; возвращает
n
sprintf(fmt, ...)
Форматирование в соответствии со спецификацией
fmt
substr(s,m,n)
Подстрока в
n
символов строки
s
, начинающаяся с индекса
m

Таблица 4.5: Встроенные функции

awk

Ассоциативные массивы

Стандартной задачей обработки данных является получение суммарных значений для множества пар имя значение. Иными словами, по входному потоку типа

Susie 400

John 100

Mary 200

Mary 300

John 100

Susie 100

Mary 100

мы хотим получить суммарные значения для каждого имени:

John 200

Mary 600

Susie 500

Программа

awk
предлагает изящное решение этой задачи — с помощью ассоциативных массивов. Хотя обычно мы представляем себе индекс массива как целое число, в
awk
любое значение можно использовать в качестве индекса. Поэтому

{sum[$1] += $2}

END {for (name in sum) print name sum [name]}

Поделиться:
Популярные книги

Запечатанный во тьме. Том 3

NikL
3. Хроники Арнея
Фантастика:
уся
эпическая фантастика
фэнтези
5.00
рейтинг книги
Запечатанный во тьме. Том 3

Первый среди равных

Бор Жорж
1. Первый среди Равных
Фантастика:
попаданцы
аниме
фэнтези
5.00
рейтинг книги
Первый среди равных

Вперед в прошлое 3

Ратманов Денис
3. Вперёд в прошлое
Фантастика:
попаданцы
альтернативная история
5.00
рейтинг книги
Вперед в прошлое 3

И.Бабель. Воспоминания современников

Паустовский Константин Георгиевич
Документальная литература:
биографии и мемуары
5.00
рейтинг книги
И.Бабель. Воспоминания современников

Здравствуй, 1985-й

Иванов Дмитрий
2. Девяностые
Фантастика:
альтернативная история
5.25
рейтинг книги
Здравствуй, 1985-й

Кодекс Охотника. Книга XXXIII

Винокуров Юрий
33. Кодекс Охотника
Фантастика:
попаданцы
аниме
фэнтези
фантастика: прочее
5.00
рейтинг книги
Кодекс Охотника. Книга XXXIII

Узы крови

Шелдон Сидни
Детективы:
прочие детективы
9.30
рейтинг книги
Узы крови

Охотник на демонов

Шелег Дмитрий Витальевич
2. Живой лёд
Фантастика:
боевая фантастика
5.83
рейтинг книги
Охотник на демонов

Ботаник

Щепетнов Евгений Владимирович
1. Ботаник
Фантастика:
фэнтези
боевая фантастика
4.56
рейтинг книги
Ботаник

Кодекс Крови. Книга ХVII

Борзых М.
17. РОС: Кодекс Крови
Фантастика:
попаданцы
аниме
фэнтези
5.00
рейтинг книги
Кодекс Крови. Книга ХVII

Когда он был порочным

Куин Джулия
6. Бриджертоны
Любовные романы:
исторические любовные романы
8.85
рейтинг книги
Когда он был порочным

Вернувшийся: Первые шаги. Том II

Vector
2. Вернувшийся
Фантастика:
боевая фантастика
космическая фантастика
рпг
5.00
рейтинг книги
Вернувшийся: Первые шаги. Том II

Простолюдин

Рокотов Алексей
1. Путь князя
Фантастика:
боевая фантастика
рпг
5.00
рейтинг книги
Простолюдин

Вечный. Книга III

Рокотов Алексей
3. Вечный
Фантастика:
фэнтези
попаданцы
рпг
5.00
рейтинг книги
Вечный. Книга III