Показать, как она работает, проще всего на конкретном примере. Предположим, у нас имеется книга в формате Plain Text, состоящая из введения и 23 глав, которую надо разбить на соответствующее количество фрагментов. Для этого сочиняется такая командная конструкция:
$ csplit -f chapter mybook.txt '/Глава/' {23}
Здесь опция -f задаёт маску имён файлов, на которые будет разбит исходный текст (то есть файл mybook.txt). Шаблон, по которому будет выполняться разбиение — слово Глава ограничено прямыми слэшами и заключено в «строгие» кавычки. А число в фигурных скобках указывает, сколько раз надо повторить процедуру разбиения по заданному шаблону. И в результате мы получаем серию файлов вида chapter##, где файл chapter00 будет включать текст от начала до первой строки со словом Глава (которая, как ни странно, будет главой первой), chapter01 — от строки Глава первая до Главы второй, и так далее. Исходный файл при этом останется в неприкосновенности.
Поиск в файлах: grep сотоварищи
В одном из предыдущих разделов говорилось о поиске файлов посредством команды find. Ныне же речь пойдет о поиске внутри файлового контента - то есть поиске текстовых фрагментов. Для этого в POSIX-системах используется семейство утилит grep — собственно grep, egrep и fgrep, несколько различющихся функционально. Впрочем, в большинстве систем все это суть разные имена (жёсткие ссылки) одной и той же программы, именуемой GNU-реализацией grep, включающей ряд функций, свойственных ее расширенному аналогу, egrep. Соответственно, поиск текстовых фрагментов в файлах может быть вызван любой из этих команд, хотя в каждом случае функциональность их будет несколько различаться.
Однако начнем по порядку. Самой простой формой команды grep является следующая:
$ grep pattern files
где pattern - искомая последовательность символов, а files - файлы, среди которых должен производиться поиск (или - просто одиночный файл). В указании имен файлов допустимы обычные маски, например, командой
$ grep line ./*
будут найдены строки вида line во всех файлах текущего каталога. Шаблон для поиска не обязан быть односложным. Правда, если в нем используются последовательности символов, разделенные пробелами, последние должны тем или иным способом экранироваться, иначе в качестве шаблона будет воспринято только первое слово. Например, каждый пробел может предваряться символом обратного слэша (\), или просто все искомое выражение заключается в одинарные или двойные кавычки.
Шаблоны могут включать в себя регулярные выражения. причём список таковых для команды grep существенно шире, чем для команд манипулирования файлами. Так, кроме маски любой последовательности символов (*), любого одиночного символа (?), списка и диапазона символов ([a...z] и [a-z]), могут встречаться:
• . (точка) - маска любого одиночного (но, в отличие от маски ?, обязательно присутствующего) символа; то есть при задании шаблона lin. будут найдены строки, содержашие line или lins, но не lin;
• ^ и $ - маски начала и конца строки, соответственно: по шаблону ^line, будут найдены строки, начинающиеся с соответствующего слова, по шаблону же line$ - им заканчивающиеся;
• маски повторения предыдущего шаблона, \{n\} - ровно n раз, \{n,\} - не менее n раз, \{,m\} - не более m раз, \{n,m\} - не менее n раз и не более m раз.
Маски повторения относятся к так называемым расширенным регулярным выражениям. Для их использования команда grep должна быть дана с опцией -e или в форме egrep — последняя часто определяется в общесистемном или пользовательском профильном файле как псевдоним команды grep:
alias grep='egrep -s'
или
alias grep egrep
в оболочках семейств shell и csh, соответственно.
При этом становятся доступными и другие возможности поиска - например, нескольких текстовых фрагментов (соедниненных логическим оператором «ИЛИ») одновременно. Делается это двояко. Первый способ - просто перечисление искомых фрагментов, каждый из которых предваряется опцией -e (и при необходимости экранируется кавычками):
$ grep -e pattern1 -e pattern2 files
При втором способе оператор между искомыми шаблонами задается в явном виде:
$ egrep 'pattern1|pattern2' files
Таким способом очень легко, например, составить оглавление для длинного текста (при наличии некоторой системы рубрикации в нем, разумеется). Для этого достаточно дать команду вроде следующей:
$ egrep 'Часть|Глава|Раздел|Параграф' filename
Для текста, включающего html- или TeX-разметку, роль рубрик могут выполнять соответствующие ее элементы, например: