Задача текстовых редакторов
После основных утилит для работы с файлами и текстом первая
программа, которая понадобится любому пользователю Linux – это текстовый редактор (для краткости – просто редактор). Из предыдущих
лекций и собственных экспериментов Мефодию уже стало понятно, какое
значительное место занимают в системе Linux данные в текстовом
формате, т. е. состоящие из символов, которые могут быть отображены
на экране терминала и которые может прочесть человек. Однако пока
Мефодий мог работать с текстом только последовательно, строка за
строкой; даже имея дело с файлом, он не мог вернуться и
отредактировать уже переданные системе строки. Именно для того, чтобы
работать с текстовым файлом как со страницей, по которой можно
перемещаться и редактировать текст в любой точке, и нужны текстовые
редакторы. Эта кажущаяся сегодня тривиальной возможность сколько угодно редактировать текст,
не оставляя при этом никаких следов, была радикальнейшим достижением прогресса по
сравнению с пишущей машинкой.
Текстовый редактор потребуется пользователю Linux в первую очередь
для того, чтобы изменить настройки системы или своего окружения,
например, shell – при этом нужно будет редактировать конфигурационные
файлы, которые всегда представлены в текстовом формате (см. лекции 8
и 12). Но и собственные задачи пользователя могут потребовать
редактирования текстовых файлов: например, сценарии и программы,
электронные письма, а также заметки для себя, которые пишет Мефодий
—все это данные в текстовом формате. Текстовые данные, полученные при
помощи стандартных утилит, тоже бывает удобно сохранять в файлах и
редактировать.
Не стоит путать текстовые редакторы и текстовые процессоры. Текстовые
процессоры, например OpenOffice Writer или Microsoft Word,
предназначены для создания документов, в которых, помимо собственно
текста, содержится и различная метаинформация (информация об
оформлении): размещение текста на странице, шрифт и т. п. Поскольку в текстовом формате не предусмотрено средств для сохранения информации
об оформлении (там есть только символы и строки), текстовые
процессоры используют собственные форматы для хранения данных. Текст,
в котором нет никакой метаинформации об оформлении, называют "plain
text" (только текст, "плоский", простой текст).
Однако при помощи текстовых редакторов можно работать не только с
форматом plain text. Различная метаинформация (об оформлении, способе
использования текста, например, в качестве ссылки и пр.) может быть
записана и в виде обычных символов (т. е. в текстовом формате ), но со
специальным соглашением, что эти символы нужно интерпретировать
особым образом: как инструкции по обработке текста, а не как текст.
Такие инструкции называются разметкой. Таким образом устроен,
например, формат HTML. Для того чтобы обработать разметку HTML и в
соответствии с ней отобразить текст, нужна специальная программа –
браузер, но редактировать файлы HTML и прочие форматы разметки можно
и при помощи текстового редактора. Кроме того, программы на любых
языках программирования и сценарии (программы на shell) тоже
представляют собой текстовые файлы. Многие текстовые редакторы
ориентированы на работу не только с "плоским" текстом, но и с текстом
в различных форматах. Для этого придумана масса усовершенствований,
уменьшающих количество символов, которые нужно вводить вручную:
специальные команды, клавиатурные сокращения и автодополнение
ключевых слов и конструкций.
Важнейшее условие для текстового редактора в Linux – возможность
работать в терминале, так как это основной способ управления
системой. Поэтому и ввод данных, и редактирование должны полностью
осуществляться средствами терминала, т. е. алфавитно-цифровыми и
некоторыми функциональными клавишами. Поскольку функциональных
клавиш, на которые можно рассчитывать на любом терминале, совсем
немного, а команд, которые нужно отдавать редактору, – очень много,
требуется способ вводить любые команды ограниченными средствами
терминала. Это условие, равно как и требование удобства при работе с
разнообразными структурированными текстами, выполнено в двух
"главных" текстовых редакторах Linux – Vi и Emacs, о которых в
основном и будет идти речь в этой лекции.
Vi и лучше, чем Vi
В любой системе Linux, даже при самой минимальной конфигурации,
всегда присутствует текстовый редактор, поскольку в любой – даже
самой катастрофической – ситуации у пользователя должна быть
возможность отредактировать конфигурационные файлы, чтобы привести
систему в рабочее состояние. По сложившейся традиции текстовым
редактором, который обязательно запустится из любой командной строки
Linux, является ViКак и большинство основных утилит и принципов, унаследованных Linux от UNIX.
Название Vi происходит от visual editor, "визуальный", экранный редактор, поскольку Vi –
первый редактор для UNIX, использующий весь экран для отображения текста и
позволяющий работать с текстом не построчно, а перемещаясь по нему в любых направлениях,
как по странице.. Однако верно и обратное: если вы работаете в
незнакомой системе Linux или произошел сбой, в результате которого
доступна только очень небольшая часть системы, нельзя быть уверенным,
что найдется хоть какой-нибудь другой текстовый редактор, кроме Vi.
Поэтому каждому пользователю Linux нужны хотя бы основные навыки
работы в Vi. При первом знакомстве c Vi работа обычно не ладится:
очень уж он непривычен, его нельзя с удобством использовать, запомнив
только две-три простейшие команды редактирования. Cтоит понять
основные принципы работы в Vi и потратить некоторое время на его
освоение, тогда в нем откроется мощный инструмент, позволяющий очень
эффективно работать с текстом.
Под именем Vi, на самом деле, может скрываться несколько разных
программ: с момента появления Vim в операционной системе UNIX (а это
произошло около 30 лет назад) этот редактор стал чем-то вроде
стандарта. К настоящему времени существует ряд программ, либо в
точности повторяющих вид и поведение "классического" Vi (например, nvi ), либо очень похожих на него, но со значительно расширенными
возможностями (Vim, elvis ). Наибольшей популярностью пользуется Vim,
возможности которого огромны – для их описания потребовалось почти
сто тысяч строк документации. Когда пользователь Linux набирает в
командной строке Vim, скорее всего, будет запущена "облегченная"
версия Vi, которая настроена таким образом, чтобы максимально
воспроизводить поведение классического редактора Vim. Естественно, в
таком режиме часть возможностей Vi недоступна. Все свойства,
которыми Vi отличается от Vim, обязательно снабжены в руководстве по
Vi указанием "not in vi". В дальнейшем изложении под Vi мы будем
понимать именно Vim в режиме совместимости, все возможности,
недоступные в этом режиме, будут оговариваться. Чтобы вызвать Vim в
полнофункциональном режиме, достаточно набрать команду Vim.
Популярность Vi не случайна: этот текстовый редактор позволяет не
только производить простые операции редактирования текстовых файлов –
он хорошо приспособлен и для максимально быстрого и эффективного
решения ряда смежных с редактированием задач. Среди самых важных его
возможностей – инструменты для работы с текстами на различных языках
программирования и в различных форматах разметки. Vim умеет
подсвечивать разными цветами синтаксические конструкции языка
программирования или разметки Обычно современные терминалы и программы-эмуляторы терминалов поддерживают
вывод текста по крайней мере несколькими разными цветами., автоматически выставлять отступы, что
облегчает восприятие структуры документа. Кроме того, в Vim есть
специальные средства для организации цикла отладки программы:
компиляция–правка исходного текста–компиляция... Подробнее об этих и
прочих возможностях Vim можно узнать из руководств по Vim. Объем
данной лекции позволяет описать только самое начало работы с Vi.
Запуск Vi
Чтобы начать сеанс редактирования в Vi, достаточно выполнить команду
Vi на любом терминале. Чтобы открыть для редактирования уже
существующий файл, путь к этому файлу нужно указать в качестве
параметра: " vi путь_к_файлу ". Как и всякая уважающая себя программа
UNIX, Vim может быть запущен с множеством модифицирующих его
поведение ключей, которые подробно описаны в руководстве. Вызванный
без параметра, редактор откроет пустой буфер – чистый лист для
создания нового текста. В центре экрана при этом может появиться
краткое приветственное сообщение, где указаны версия программы и
команды для получения помощи и выхода из редактора (что
нетривиально). Однако такое сообщение может и не появиться – это
зависит от версии Vi, установленной в системе.
Для отображения текста и работы с ним Vi использует весь экран
терминала – только последняя строка предназначена для диалога с
пользователем: вывода информационных сообщений и ввода команд. Пока буфер не заполнен текстом, в начале каждой строки экрана отображается
символ " ~ ", обозначающий, что в этом месте буфера нет ничего, даже
пустой строки. Общий вид экрана в начале работы будет примерно такой:
#
~
~
~
~
~
Символ " # " обозначает курсор. На экране терминала умещается больше
строк, но в примерах мы будем для компактности изображать только
необходимый минимум.
Режимы
В Vi проблема разделения команд редактору и вводимого текста решена
при помощи режимов: в командном режиме нажатие на любую клавишу – это
команда редактору, в режиме вставки нажатие на клавишу приводит к
вставке соответствующего символа в редактируемый текст. Поэтому при
работе с Vi пользователю всегда нужно обращать внимание на то, в
каком режиме находится редактор.
Режимы Vi. Состояния редактора Vi, в которых он по-разному обрабатывает нажатия
клавиш. Различают три режима Vi: командный (нажатие любой клавиши
считается командой и немедленно исполняется), вставки (нажатие
клавиши-печатного символа приводит к вставке этого символа в текст) и командной строки (для ввода длинных команд, отображаемых на экране;
ввод завершается Enter ).
Редактор Vi всегда начинает работу в командном режиме. В этом режиме
есть два способа отдавать команды редактору. Во-первых, нажатие
практически на любую клавишу редактор воспринимает как команду. В
Vim, даже в режиме Vi-совместимости, командное значение определено
для всех латинских букв (в верхнем и нижнем регистрах ), цифр, знаков
препинания и большинства других печатных символов. При нажатии на эти
клавиши вводимые команды нигде не отображаются – они просто Не нужно пытаться вводить текст в командном режиме: поскольку у каждой буквы есть
командное значение, результат может быть самым неожиданным!
Во-вторых, у Vi есть своя командная строка: чтобы ее вызвать, нужно
ввести в командном режиме " :". В результате в начале последней строки
экрана появится двоеточие – это приглашение командной строки. Здесь
вводятся более сложные команды Vi, которые включают в себя целые
слова (например, имена файлов), причем текст набираемой команды,
конечно, отображается. Команды передаются Vi клавишей Enter. В
современных версиях Vim с командной строкой можно работать так же,
как и в shell: редактировать ее, достраивать команды клавишей Tab,
пользоваться историей команд.
Главная команда командной строки Vim – вызов подсистемы помощи " :help
Enter ". Двоеточие переводит Vim в режим командной строки, " help " –
собственно команда, Enter передает команду. help можно вызывать с
аргументом: названием команды или настройки Vim. Vim очень хорошо
документирован, поэтому по команде " :help объект " можно получить
информацию о любом свойстве Vim, например, команда " :help i " выведет
сведения о значении клавиши " i " в командном режиме Vi.
Команда " :set имя_настройки " позволяет настраивать Vim прямо в
процессе работы с ним. Например, отдав команду " :set wrap "
пользователь тем самым включает настройку " wrap ", что заставляет
редактор переносить слишком длинные строки, не умещающиеся в ширину
терминала. Выключить эту настройку можно командой " :set nowrap ", так
что концы длинных строк исчезнут за правым краем экрана.
Наконец, чтобы ввести текст, нужно перейти из командного режима в
режим вставки, нажав клавишу " i " (от " i nsert" – "вставка"). В этот
момент в последней строке появится сообщение о том, что редактор
находится в режиме вставки: " Если используется не Vim, или настройка showmode по умолчанию запрещена,
сообщения может и не быть., в
зависимости от установленного языка системных сообщений.
В режиме вставки можно вводить текст, завершая строку нажатием Enter.
Однако нужно помнить, что в некоторых (ортодоксальных) версиях Vi в
режиме ввода не работают никакие команды перемещения по тексту –
здесь можно только набирать. Если вы заметили, что ошиблись в наборе
– не нужно сразу перемещать курсор и пытаться исправить ошибку:
гораздо удобнее будет внести все исправления потом, в командном
режиме, где доступно множество специальных команд быстрого
перемещения и замены текста. Чтобы перейти из режима вставки обратно
в командный режим, нужно нажать Если Vim пришел в непонятное для вас состояние, нажмите ESC, чтобы вернуться в
командный режим (иногда требуется нажать ESC дважды).
Мефодий начал упражняться с Vim на файле примеров:
methody@oblomov:~ $ vi textfile
Это файл для примеров.
Пример 1.
~
~
~
~
~
"textfile" 2L, 33C 1,1 Весь
Vim начал работу, как и положено – в командном режиме. В последней
строке содержатся некоторые полезные сведения об открытом файле: его
имя, общее количество строк (" 2L "), символов (" 33С "), позиция курсора
(" 1,1 " – номер_строки,номер_символа). " Весь " обозначает, что все
содержимое файла уместилось на экране терминала. Теперь Мефодий
нажмет " i " и введет немного текста:
Это файл для примеров.
Пример 1.
Моя первая строка в vi!
~
~
~
~
-- ВСТАВКА -- 3,24 Весь
Теперь Vim работает в режиме вставки: в последней строке появилось
информационное сообщение об этом. Набрав текст, Мефодий может
вернуться в командный режим, нажав ESC (подсказка " --ВСТАВКА-- " при
этом исчезнет из последней строки).
На самом деле, из командного режима можно перейти в режим ввода
несколькими командами. Разница между ними заключается в том, в какой точке начнется ввод символов. Например, по командам " O " и " o "
(" o pen") можно вводить текст с новой строки (до или после текущей),
по команде " I " – с начала строки, команды " a " и " A " (" a ppend") ведают добавлением символов (после курсора или в конец строки) и т. п.
Работа с файлами
Редактируя текст в Vi, пользователь работает не непосредственно с
файлом, а с буфером. Если открывается уже существующий файл, Vi
копирует его содержимое в буфер и отображает буфер на экране. Все
изменения, которые производит пользователь, происходят именно в
содержимом буфера – открытый файл пока остается неизменным. Если же
Vi вызван без параметра, то создается пустой буфер, который пока не
связан ни с каким файлом В действительности содержимое буфера хранится в специальном временном файле (swap
file). Если сеанс работы в редакторе по какой-то причине прервался, то этот временный
файл не будет удален, и при следующей попытке продолжить незаконченную работу с
файлом Vi предложит провести процедуру восстановления – на случай, если во временном
файле остались несохраненные изменения..
Чтобы записать сделанные изменения в файл, используется команда
" :wEnter " (чтобы ее отдать, нужно сначала перейти в командный режим).
О том, что " w " – это сокращение от англ. " w rite", "записать", можно
узнать, нажав Tab после " :w " – и Vim дополнит эту команду до " write ".
Подобным образом можно поступить с большинством команд в командной
строке Vim – в этом редакторе очень последовательно соблюдается
принцип аббревиативности. Мефодий выполнил " write " и получил такое
информационное сообщение:
Это файл для примеров.
Пример 1.
Моя первая строка в vi!
~
~
~
~
"textfile" 3L, 57C записано 3,24 Весь
Мефодий не указал, куда именно записать содержимое буфера, и по
умолчанию оно было записано в тот файл, который он и открывал для
редактирования: " textfile ". Однако команде " write " можно указать
любое имя файла в качестве параметра – и тогда содержимое буфера
будет записано в этот файл, а если такого файла нет, то он будет
создан. Параметр " write " обязательно потребуется, если текст в буфере
еще не записан ни в каком файле.
Наиболее важна для новичка команда выхода из Vi – " :qEnter "
(сокращение от " q uit"). Пользователь, запустивший редактор в первый
раз, нередко сталкивается с тем, что никак не может его закрыть: не
работает ни один из привычных способов завершения программы, даже
" ^C " Vi обрабатывает по-своему*. И " :w ", и " :q " – команды режима
командной строки; в этот режим Vi переводится из командного режима с
помощью " :", набираемого в начале команды.
Однако если в буфере есть изменения, которые еще не записаны ни в
каком файле, то Vi откажется выполнять команду " :q ", предложив
сначала сохранить эти изменения. Если вы не хотите сохранять
изменения, нужно настоять на своем желании выйти из Vi, добавив к
команде выхода восклицательный знак: " :q!". В этом случае все
несохраненные изменения будут выброшены. Восклицательный знак можно
добавить в конце любой файловой команды в командной строке Vi – в
этом случае Vi будет без возражений выполнять команды.
В Vi предпринято множество усилий для экономии сил и времени
пользователя, командующего редактором. Поэтому можно одним разом
записать текст и выйти из редактора: командой " :wq " или аналогичной
командой " :x ", просто нажав " ZZ " в командном режиме.
Перемещение по тексту
При редактировании в тексте всегда есть точка, в которой пользователь
"находится" в данный момент: вводимые с клавиатуры символы появятся
именно здесь, удаляться символы будут тоже отсюда, к этой точке будут
применяться команды редактора и т. п. Обычно эта точка обозначается
курсором, а в последней (информационной) строке экрана Vim указывает
номера текущей строки и колонки (номер символа в строке), в которых
находится курсор.
Для того чтобы выполнять редактирование текста, по нему необходимо
перемещаться, т. е. перемещать курсор. Самый очевидный способ это
делать – воспользоваться клавишами со стрелками. Нажатие на одну из
этих клавиш обычно заставляет курсор перемещаться на один символ
влево/вправо или на одну строку вверх/вниз. Трудно придумать более
неэффективный и медленный способ перемещения, если нужно попасть на
другой конец объемного текста, и даже простое перемещение к началу или
концу строки может занять несколько секунд.
Заметим, что в процессе редактирования текста обычно возникает
необходимость перемещаться не в произвольную точку, а в некоторые
ключевые: начало и конец строки, слова, предложения, абзаца,
выражения, заключенного в скобки, целого текста. Особенно это
заметно, если требуется редактировать структурированный текст:
программу (например, сценарий), конфигурационный файл и т. п. В Vi
для каждого такого перемещения предусмотрены специальные команды,
обычно состоящие в нажатии одной клавиши в командном режиме.
Используя их, можно не только нажав одну кнопку переместиться на любое
расстояние в тексте, но и двигаться по структурным элементам,
переходя к предыдущему/следующему слову, предложению, абзацу, скобке
и т. д. Прежде чем начинать экспериментировать с перемещением, нужно перейти в командный
режим.
Итак, передвинуть курсор на начало текущей строки можно командой " 0 ",
на первый непробельный символ в строке – " Символами " ^ " и " $ " в Linux повсеместно обозначаются начало и конец строки, в
частности, в регулярных выражениях .
Абзацами Vi считает фрагменты текста, разделенные пустой строкой, к
началу предыдущего/следующего абзаца можно попасть командами " { " и " } "
соответственно. Очень распространенная задача – необходимость попасть
в самый конец файла: для этого служит команда " G " (" G o"), в самое
начало – " gg ".
Передвинуть курсор вперед на начало следующего слова можно командой
" w " (от "word", слово), на начало предыдущего – " b " (от " b ackward",
назад). К началу предыдущего/следующего предложений можно
переместиться командами " ( " и " ) " соответственно. Нужно учитывать,
что границы слов и предложений Vi находит по формальным признакам
(руководствуясь специально определенными регулярными выражениями ),
поэтому решение Vi может иногда не совпадать с представлениями
пользователя о границах слов и предложений. Однако пользователь
всегда властен изменить соответствующие регулярные выражения,
подробности – в документации по Vim.
В Vim никогда не следует вручную повторять одну и ту же команду: если
нужно перейти на три слова вперед, не следует трижды нажимать " w " –
для повторения команды используется множитель. Множитель – это любое
число, набранное перед командой Vi: команда будет повторена
соответствующее число раз. Например, " 3w " – означает "трижды
переместить курсор на слово вперед", иначе говоря, переместить курсор
на три слова вперед. Обратите внимание, что множители могут
применяться не только с командами перемещения, но и с любыми
командами Vi. Аналогично можно переместить курсор на 10 абзацев
вперед командой " 10} ".
Множитель. Число, предшествующее команде Vim и означающее, что данную команду
следует выполнить указанное число раз.
Не сразу очевидно, что поиск шаблона в тексте (строки или регулярного
выражения ) – это тоже команда перемещения. Как и любое перемещение,
поиск осуществляется в командном режиме: прежде всего, нужно нажать
" / ": в последней строке появится символ " / ". Далее следует ввести
шаблон для поиска – он будет отображаться в этой строке, его можно
редактировать. Обычно Vi настроен таким образом, что шаблон для
поиска интерпретируется как регулярное выражение, где ряд символов
имеет специальное значение, эту настройку можно отключить (" :set
nomagic "). После того, как введен шаблон, следует нажать Enter –
курсор переместится к ближайшему (далее по тексту) совпадению с
шаблоном. Поиск в обратном направлении (к предыдущему совпадению)
следует начинать с команды " ?".
Совсем просто перейти к следующему употреблению в тексте того слова,
на котором стоит курсор: для этого нужно просто нажать " * " в
командном режиме. Аналогичная команда поиска слова в обратном
направлении – " # ". Можно специально отметить в тексте точку и затем в
любой момент возвращаться к ней, как к закладке. Одну закладку
определяет сам Vi – " `` ", место в тексте, где было сделано последнее
изменение. Подробно об этих и других командах перемещения можно
прочесть в руководстве по Vim по команде " :help usr_03.txt ".
Изменение текста
В командном режиме нельзя вводить символы в текст с клавиатуры, но
изменить текст при этом можно, например, удаляя символы. Чтобы
удалить отдельный символ (тот, на котором стоит курсор), достаточно
нажать " x " в командном режиме, а чтобы удалить сразу целую строку
(естественно, текущую, то есть ту, в которой находится курсор) –
" dd ". " d " – это сокращение от " d elete", удалить, а " dd " – характерный
прием Vi: удвоение команды означает, что ее нужно применить к текущей
строке.
Из командной строки Vi можно выполнить операцию поиска и замены: для
простой строки или для регулярного выражения. Причем синтаксис
команды поиска и замены полностью воспроизводит синтаксис потокового
редактора sed, о котором уже шла речь в лекции 7:
Это файл для примеров.
Пример 1.
Моя первая строка в vi...
~
~
~
:s/.$/.../
Мефодий хотел заменить в своем файле точки в концах строки
многоточиями. Для этого в командном режиме он нажал " :" (вызов
командной строки Vi), где набрал команду " s " (сокращение от
"substitute", заменить), за которой следует уже знакомое по "sed"
выражение " /что_заменить/на_что_заменить/ ". Только результат
получился совсем не тот, какого ожидал Мефодий: заменился на
многоточие восклицательный знак последней строки. Не учел он
следующего: по умолчанию шаблоны для поиска и замены – это регулярные
выражения, то есть " ." означает вовсе не точку, а "любой символ".
Имея в виду точку, следовало написать " \.". " $ ", как и ожидал
Мефодий, это конец строки. В момент выполнения команды поиска курсор
находился в последней строке, в первом совпадении после курсора и
была произведена замена.
Форматирование текста – это расстановка символов конца строки,
пробелов и табуляций таким образом, чтобы текст хорошо смотрелся на
экране терминала. Форматирование вручную крайне неэффективно. В Vim
автоматическое форматирование текста (если редактируется программа на
каком-либо языке программирования, то с учетом правил этого языка)
может происходить прямо в режиме вставки, в режиме вставки же можно
изменять отступ текущей строки (по командам " ^D " и " ^T "). Для
выравнивания текста по центру, правому или левому краю команды
" :center ", " :left " и " :right " соответственно. Эти команды, как и
большинство команд командной строки, можно применять к диапазону
строк способом, описанным ниже.
Режим ввода не богат специальными командами изменения текста, что и
понятно: он предназначен для ввода. Однако в Vim (но не в Vi!) есть
некоторые удобства, упрощающие и сам процесс набора. Если слово,
которое нужно ввести, уже встречалось в тексте, можно набрать только
первые буквы и нажать " ^P " (" p revious") – Vim попробует сам завершить
его. Если Vim не угадал и предложил не то слово, можно продолжить
перебирать варианты. Команда " ^N " (" n ext") подставляет слова, которые
встречаются ниже по тексту. Подробнее об этой функции можно узнать из
руководства по команде " :help ins-completion ".
Иногда пользователь, изменив текст, тут же хочет вернуть все обратно.
Для этого в Vi предусмотрена команда отмены последнего изменения: " u "
в командном режиме (от " u ndo", отменить). Каким бы сложным,
масштабным (и разрушительным) ни было изменение, совершенное
последней командой, " u " вернет текст в исходное состояние. Впрочем,
саму отмену тоже можно отменить. В классическом Vi доступна отмена
только последней выполненной команды, а в Vim отменить можно сколько
угодно последних команд, а также повторить их командой " ^R ".
Работа с фрагментами текста
Любая команда перемещения определяет две точки в тексте: ту, в
которой был курсор до перемещения, и ту, в которую он переместился в
результате данной команды. Расположенный между этими двумя точками
отрезок текста однозначно задается командой перемещения. Например,
команда " ) " захватывает текст от текущего положения курсора до начала
следующего предложения. Vi позволяет применить к этому фрагменту любую
команду редактирования – так устроены гнездовые команды. Гнездовая
команда состоит из действия и следующего за ним перемещения.
Перемещение задает фрагмент текста, а действие определяет, что с этим
фрагментом сделать. Например, команда " d) " удалит весь текст от
текущей позиции курсора до начала следующего предложения. Наиболее
полезные действия – " d " (" d elete"), " c " (" c hange"), " > " и " < "
(сдвинуть), " y " (запомнить) и " gq " (отформатировать).
Гнездовая команда. Команда редактора Vi, позволяющая применить указанное действие к
указанному отрезку текста. Отрезок задается стандартной командой
перемещения по тексту.
Очень часто возникает необходимость заменить фрагмент в тексте:
слово, предложение, строку и т. д. Это можно сделать в два действия:
сначала удалить часть текста, затем перейти в режим вставки и
вставить замену. Vi предоставляет возможность упростить эту операцию,
сведя два действия к одному: заменить. Гнездовая команда " c "
предназначена именно для этого. Например, команда " cw " (буквально:
" c hange w ord") заменит текст от курсора до начала следующего слова
(так можно заменить одно слово), " c) " заменит текст от курсора до
начала следующего предложения.
Мефодий не забыл, что команды перемещения можно использовать с множителями, и попробовал заменить сразу три слова в своем файле на
другие: для этого он в командном режиме подогнал курсор в начало
слова "первая" и набрал " c3w " ("заменить фрагмент отсюда до начала
третьего слова", буквально: "change 3 words"). Результат этой команды
выглядел так:
Это файл для примеров.
Пример 1.
Моя #vi...
~
~
~
-- ВСТАВКА -- 3,5 Весь
В примере знак " # " обозначает позицию курсора: как видно, Vi удалил
три слова, попавшие в зону действия команды и сразу перешел в режим
вставки. Мефодию осталось только набрать что-то взамен.
Перестановка частей – типичная задача, возникающая в процессе
редактирования. Для перестановки требуется удалить фрагмент в одном
месте текста и вставить его же в другом. Для решения первой части
задачи в Vi нет специальных средств, потому что любая команда
удаления (" d ", " c ", " x " и др.) сохраняет удаленный текст в
специальном регистре. Для вставки последнего удаленного фрагмента
служит команда " p " в командном режиме (от " p ut", положить). При
помощи этой команды Мефодий может вставить только что удаленные им
командой " c3w " три слова:
Это файл для примеров.
Пример 1.
Моя новая строка для vi...
первая строка в
~
~
4,1 Весь
Для того чтобы скопировать фрагмент текста, служит команда " y " (от
" y ank" – забрать, сдернуть): она не удаляет текст, а просто сохраняет
его в том же регистре, что и команды удаления. Команду " y " можно
использовать в гнездовых командах, например, " y5w " сохранит в регистре фрагмент текста от курсора до начала пятого слова. Вставить
скопированный фрагмент можно все той же командой " p ". Однако таким
способом можно вставлять только текст, удаленный или скопированный последним, для хранения нескольких разных фрагментов текста следует использовать
именованные регистры (см. подробнее в руководстве по Vim).
Для того чтобы применить команду к нескольким строкам текста, не
обязательно подгонять к ним курсор. В командной строке Vi любой
команде может предшествовать указание диапазона в тексте, к которому
следует эту команду применить. Команды с указанием диапазона выглядят
так: " :начало,конец}команда ", где начало и конец – это адреса
начальной и конечной строк диапазона (т. е. фрагмента текста), а команда – это команда режима командной строки, такая как " :w " или
" :r ". Многие команды командного режима (в частности, " d " и " y ")
доступны также и в командной строке. В качестве адреса можно
использовать номера строк в файле (команда " :1,5y " будет означать
"скопировать в регистр строки с первой по пятую"), есть специальные
обозначения для текущей строки (" ."), последней строки (" $ ") и всего
файла (" % "). Указать границу диапазона можно и при помощи шаблона:
граничной будет считаться та строка, в которой обнаружится шаблон.
Последним свойством Мефодий воспользовался, чтобы удалить плоды своих
экспериментов: он выполнил команду " :/Пример 1/,$d " (от строки
" Пример 1 " до конца файла – удалить):
Это файл для примеров.
~
~
~
3 fewer lines
Настройка Vi и Vim
Вид и поведение Vi и Vim можно существенно изменить при помощи
настроек, приспособив редактор именно к своим вкусам и привычкам.
Прямо во время работы редактора можно менять настройки из командной
строки Vi при помощи команды " :set имя_настройки ". Кроме того, можно
сделать настройку постоянной, вписав все нужные значения в конфигурационный файл .vimrc (или .exrc – для Vi) в домашнем каталоге
пользователя. При каждом запуске Vim/Vi читает этот файл и исполняет
все содержащиеся в нем команды. Объем лекции не позволяет подробно
остановиться на настройке Vi, читатель может заняться изучением этого
вопроса сам: все необходимые сведения есть в руководствах. Чтобы
оценить возможности настройки, можно выполнить в Vim (но не в Vi!)
команду " :options ", по которой будет выведен список всех доступных
опций с кратким описанием их смысла.
Лучше, чем Emacs?
Заголовок этого раздела сформулирован таким провокационным образом не
случайно: любому пользователю похожей на UNIX операционной системы (к
таким системам относится и Linux) необходим текстовый редактор. Выбор
очень многих пользователей падает на один из двух наиболее популярных
и, как следствие, наиболее универсальных (реализованных и работающих
везде) текстовых редактора: Vi (или одну из его версий, чаще всего
Vim) и Emacs. Оба эти редактора появились около тридцати лет назад,
но почтенный возраст им на пользу: огромное количество разработчиков по всему миру
все эти годы занималось их отладкой, локализацией и расширением.
Vim и Emacs образуют альтернативную пару не только по исторической
случайности: оба редактора претендуют на роль универсального средства
для работы с текстом на любых естественных и искусственных языках. И
действительно, трудно назвать сравнимый с ними по возможностям текстовый редактор, да еще и настолько нетребовательный к интерфейсу:
и Vim, и Emacs будут работать на любом терминале. Однако ограниченные
возможности интерфейса терминала требуют от программ надежного
способа отделения команд редактора от вводимого текста. В Vi и Emacs
эта задача решена по-разному – отсюда и большая часть различий в
стиле работы с этими редакторами, и традиционный спор приверженцев
этих редакторов о том, какой из них лучше.
Тексты на разных языках
Главное свойство, которое сделало Emacs таким популярным и
многофункциональным редактором – это заложенная в нем с самого начала
принципиальная расширяемость. Emacs почти полностью написан на
специально созданном для него языке программирования Emacs Lisp, и у
любого пользователя есть возможность запрограммировать необходимые именно ему функции и подключить их в качестве модуля к Emacs. При
этом сам Emacs никак изменять не требуется. Сообщество программистов
не замедлило воспользоваться расширяемостью Emacs, и к настоящему
времени важнейшее достоинство этого редактора состоит именно в
свободно распространяемых пакетах расширений, содержащих инструменты
для решения самых разнообразных задач, связанных с редактированием
текста.
Современный Emacs – это не просто текстовый редактор, а
интегрированная среда для работы в системе. Основная идея сообщества
разработчиков и пользователей Emacs состоит в том, что Emacs
позволяет работать с любыми данными, которые могут быть представлены
как текст (в лекции 7 обсуждалось, что таким образом можно
представить очень многое в системе). Естественно, список содержащихся
в каталоге файлов, программа на каком-либо языке программирования или
электронное письмо – это тексты, которые сильно различаются по
структуре и по тому, что от них нужно пользователю. В Emacs для
работы с текстами разного типа используются режимы. Обратите внимание, что в Emacs понятие "режим" имеет совершенно иной смысл, чем в Vi!
Режим Emacs. Комплекс команд и настроек Emacs, предназначенных для работы с
текстом определенной структуры, например содержимым каталога,
программой на Си и. т. п.
Каждый буфер в Emacs находится в одном из основных режимов. Основной
режим – это набор функций и настроек Emacs, приспособленных для
редактирования текста определенного вида. Каждый основной режим
по-своему переопределяет некоторые управляющие символы, так что
наиболее доступными становятся команды, чаще всего именно для работы
с текстом данного типа. Команды, специфичные для текущего основного
режима, обычно начинаются с управляющего символа C-c. Некоторое
представление о возможностях Emacs может дать весьма неполный список
тех текстов, для которых существуют основные режимы:
список файлов в каталоге;
программы на самых разных языках программирования, от Си до самых
экзотических;
тексты в различных форматах разметки: XML, HTML, TeX;
словари;
электронная почта (режим позволяет не только читать и писать
письма, но и отправлять и получать их);
календарь;
дневник и личное расписание;
многое другое.
Когда требуется много и быстро работать с текстом на каком-либо
искусственном языке (языке программирования, разметки и пр.),
возможно, Emacs – это лучший выбор.
Не хуже в Emacs развиты и средства работы с текстами на разных
естественных языках с самыми экзотическими письменностями. Просто для
оценки возможностей Emacs в этой области можно выполнить команду " C-h
h ", по которой будет выведен файл, изображающий приветствие на разных
языках.
Команды Emacs
Если в вашей системе установлен Emacs, то вы можете его запустить,
набрав emacs в командной строке любого терминала. Как и Vim, Emacs
использует весь экран терминала, хотя интерфейс у него более богатый:
вверху экрана находится строка с пунктами меню, под ней – окно для
отображения и редактирования текста, которое заканчивается строкой режима, отображаются сведения о происходящем в окне. В самом низу
экрана – строка минибуфера, используемая для диалога с пользователем,
в частности для отображения и редактирования вводимых команд.
Vi и вслед за ним Vim – это многорежимные редакторы, когда команды
вводятся в одном режиме, а текст – в другом, что позволяет
использовать в качестве командных любые клавиши. В Emacs нет
специального командного режима, но использован тот факт, что с
клавиатуры можно вводить не только печатные, но и некоторые управляющие символы. Для этого используются несколько управляющих
клавиш терминала (прежде всего Ctrl и Alt ), нажатые в сочетании с
различными текстовыми символами. Чтобы ввести такой символ, нужно
нажать управляющую клавишу (например, Ctrl ) и, удерживая ее, нажать
клавишу с одним из печатных символов (например, " x "). Кроме того, в
Emacs используется управляющая клавиша Meta. На тех терминалах, где
она отсутствует, ее функции обычно передаются клавише Alt. На
"настоящих" терминалах обычно не бывает ни Meta, ни Alt ; из клавиатурных модификаторов присутствуют только Ctrl и Shift. Тогда на
помощь приходит старая добрая ESC: нажатие ESC, а после нее –
печатного символа (того же " x ") эквивалентно " Meta x ".
Команд в редакторе Emacs чрезвычайно много, доступных управляющих
символов на всех не хватает, поэтому чтобы вызвать команду Emacs,
обычно требуется ввести ключ, начинающийся с управляющего символа, за
которым следует комбинация из управляющих или обычных символов,
просто полное имя команды. Последовательность символов, достаточная
для вызова команды, называется законченным ключом, а если введенных
символов недостаточно для однозначного определения команды, это – префиксный ключ .
Общее правило здесь таково: чем чаще встречается команда, тем короче вызывающий
ее ключ, и наоборот. Для лаконичной записи длинных клавиатурных
комбинаций в сообществе пользователей Emacs сложилась особая традиция
сокращенных обозначений. Клавишу Ctrl обозначают заглавной буквой
" За свои длинные команды из разных комбинаций управляющих клавиш название Emacs
получило шуточную расшифровку: Escape-Meta-Alt-Control-Shift.. Сочетания с командной клавишей обозначаются
дефисом, например, запись С-h обозначает, что нужно, удерживая Ctrl,
нажать " h ". C-h – это префиксный ключ для команд справочной системы
Emacs. Начинающему пользователю стоит выполнить команды " C-h?"
(набрать ?") – справка по командам помощи, " C-h
t " – интерактивный учебник для начинающих пользователей Emacs, и " C-h
i " – полное руководство по Emacs (в формате info ). С ключа C-x
начинаются основные команды Emacs, в частности, для работы с файлами
и буферами. Чтобы завершить работу Emacs, нужно ввести " C-x C-c ".
У любой команды Emacs есть собственное имя. По этому имени можно
вызвать команду, даже если она не привязана ни к какому клавиатурному
ключу. Для вызова команд по имени используется префиксный ключ M-x.
Например, посмотреть справку о помощи в Emacs можно командой " M-x
help-for-help ".
Работа с файлами
В Emacs, как и в Vim, пользователь редактирует текст не в самом файле,
а в буфере. Отличие Emacs в том, что нельзя написать "безымянный"
текст и затем сохранить его в файле. При запуске Emacs без параметров
открывается специальный буфер – " *scratch* ". Он предназначен для
временных заметок – его содержимое будет выброшено при закрытии
Emacs. Если нужно создать новый файл – его следует открыть командой
" C-x C-f ", точно так же открывается для редактирования уже
существующий файл.
После того как Мефодий нажал " C-x C-f ", в минибуфере возникло
приглашение: " Find file: ~/ ". Теперь нужно ввести путь к файлу,
начиная с текущего каталога (Emacs любезно подсказал его Мефодию). С
текстом в минибуфере можно обращаться почти так же, как с командной
строкой shell или Vim: редактировать, использовать автодополнение
(клавишей Tab ), перемещаться по истории стрелочками вверх/вниз.
Мефодий не замедлил воспользоваться этой возможностью и, набрав " te ",
нажав Tab и Enter, приступил к редактированию того же " textfile ".
Сохранить сделанные изменения можно командой " C-x C-s ".
Когда Мефодий захотел открыть еще один буфер, чтобы выполнить один из своих
сценариев, он забыл точное название нужного файла и, набрав " C-x C-f
bin/ ", нажал Enter. В окне возник список файлов в подкаталоге
" ~/bin ", похожий на вывод ls -l:
File Edit Options Buffers Tools Operate Mark Regexp Immediate Subdir Help
/home/methody/bin:
итого 24
drwxr-xr-x 2 methody methody 4096 Дек 2 15:21 .
drwx------ 10 methody methody 4096 Дек 2 15:21 ..
-rwxr-xr-x 1 methody methody 26 Ноя 9 21:34 loop
-rwxr-xr-x 1 methody methody 23 Ноя 9 21:34 script
-rwxr-xr-x 1 methody methody 32 Ноя 9 21:34 to.sort
-rwxr-xr-x 1 methody methody 44 Ноя 9 21:34 two
-RRR:%%-F1 bin (Dired by name)--L5--C51--All--Reading directory /home/methody/bin/...done
Как указано в строке режима, это Dired, редактор каталогов, режим
Emacs, предназначенный для просмотра и изменения каталогов прямо из
редактора. В Dired можно выбирать отдельные файлы или группы файлов и
производить над ними различные действия: открыть для редактирования,
удалить, скопировать, переместить, переименовать по определенной схеме
и т. д. Одним словом, Dired – довольно мощное средство для наглядной
работы с файловой системой, особенно он удобен для работы с группой
файлов. Подробности о командах, доступных в этом режиме, можно найти
в руководстве по Emacs.
Перемещение по тексту
В Emacs, как и в Vim, есть понятие " точка " – то место в буфере, где
будет происходить вставка или удаление данных. Перемещение по тексту
– это перемещение точки. Команды перемещения по структурным элементам
текста развиты не менее, чем в Vim – помимо обычных стрелок,
действуют команды перемещения в начало и конец строки ( C-a и C-e ), буфера ( M-< и M-> ), предложения ( M-a и M-e ), к предыдущему и
следующему слову ( M-f и M-b ), абзацу ( M-{ и M-} ). Различные основные
режимы предоставляют специализированные команды для перемещения по
структурным элементам текстов на разных языках программирования, разметки и др.
В Emacs несколько видов поиска: существуют отдельные команды для
поиска строки и поиска по регулярному выражению. Если требуется найти
ближайшее употребление конкретного слова, удобнее всего
воспользоваться наращиваемым поиском по команде C-s. Наращиваемый
поиск уже встречался Мефодию: так был устроен поиск по истории команд
в bash. По мере набора первых символов искомой строки Emacs переносит точку к ближайшему подобному сочетанию символов после курсора. Поиск
в обратном направлении (к началу буфера ) осуществляется командой C-r. Наращиваемый поиск можно выполнять по регулярному выражению ( C-M-s ).
Все виды наращиваемого поиска в Emacs не различают прописные и
строчные буквы.
Изменение текста
В Emacs есть множество команд, позволяющих пользователю выполнять
меньше действий при редактировании текста. Если пользователь
осознает, что набрал что-то неправильно, он может разом удалить
последнее слово ( M-Del ) или предложение ( C-x Del ). Можно уничтожать и
вперед: до конца слова ( M-d ) и предложения ( M-k ). Emacs хранит не
только последний удаленный фрагмент, но и все предыдущие, формируя список удалений. Только что уничтоженный текст можно вставить
командой C-y. После этого его можно заменить предыдущим уничтоженным
фрагментом – M-y. Можно двигаться и далее назад по списку удалений,
повторяя M-y.
Хорошо продуманы команды для перестановки частей текста вокруг точки:
двух знаков ( C-t ), слов ( M-t ), строк ( C-x C-t ). Команда M-t не
перемещает знаки препинания между словами, поэтому " потеха, дело "
превратится в " дело, потеха ".
Прямо из Emacs можно вызвать программу проверки орфографии (" M-x
ispell-buffer ") или даже включить проверку "на лету", когда
неправильно написанные слова выделяются другим цветом (" M-x
flyspell-mode "). Можно проверить написание отдельного слова, в
котором находится точка (" M-x $ ") или завершить недописанное слово,
основываясь на орфографическом словаре (" M-x Tab ").
В Emacs так много специальных команд для изменения текста, что
команды поиска и замены бывают нужны не так часто. Произвести замену
строки всюду в буфере можно по команде " M-x replace-string что
заменить Enter на_что_заменить Enter ", а для замены регулярного
выражения существует аналогичная команда " M-x replace-regexp ".
Если нужно заменить строку только в некоторых случаях, пригодится
команда M-%, запрашивающая подтверждение о замене при каждой
найденной строке. Аналогичная команда для регулярных выражений – C-M-%.
Любые изменения в тексте можно отменить командой C-_ (нужно нажать Ctrl, Shift и " - ").
Работа с фрагментами текста
Многие команды Emacs работают с произвольным фрагментом текущего буфера. Такие команды всегда применяются к текущей области. Область –
это отрезок текста между точкой (где находится курсор) и меткой. Метка в любой момент присутствует в любом буфере, пользователь может
установить ее в любом месте текста явно – командой M-Пробел. Метка
может перемещаться и без вмешательства пользователя: команды
перемещения и редактирования могут изменять положение метки. Таким
образом, чтобы выделить в буфере фрагмент текста, можно проделать
следующие операции:
переместить точку (курсор) на один конец нужного фрагмента;
нажать M-Пробел (установить метку );
переместить точку к другому концу нужного фрагмента.
Теперь можно выполнять команду редактирования – она будет применена
именно к выделенной области. Например, C-w удалит текст области, а M-w скопирует его. Вставить удаленный или скопированный фрагмент
можно командой C-y.
Есть группа команд, позволяющих работать с меткой более эффективно:
установить метку после конца следующего слова ( M-@ ), пометить текущий
абзац ( M-h ) или весь буфер (" C-x h "). Различные основные режимы
предоставляют команды для пометки структурных элементов текста,
например, разделов документа, определения функции (в тексте
программы) и т. п. Все положения метки хранятся в списке пометок,
перенести точку в любое из предшествующих положений метки можно,
нужное количество раз повторив команду " C-u C-@ ".
Область. Непрерывный отрезок текста, ограниченный точкой с одной стороны и меткой с другой.
Как и в Vim, в Emacs можно использовать для хранения информации регистры. В регистре Emacs можно сохранить позицию в буфере и затем
перейти к этой позиции (" C-x r Пробел x " записывает позицию точки в регистр " x ", а " C-x r j x " переходит в эту позицию). В регистре можно
сохранить текст из области (" C-x r s x " сохраняет область в регистре
" x ", " C-x r i x " – вставляет текст из этого регистра ). В регистрах
также можно хранить числа, имена файлов, конфигурацию окон.
Подробности, как всегда, в руководстве.
Настройка Emacs
Коротко говоря, в Emacs можно настроить все: связи между ключами и
командами редактора, определить макрокоманды, написать собственные
расширения. Есть возможность изменять настройки Emacs как в процессе
работы, так и при помощи конфигурационного файла .emacsrc.
Просто текстовые редакторы
И в Vim, и в Emacs интегрировано множество средств для автоматизации
процесса редактирования. Эти редакторы становятся удобны в том
случае, если прежде чем делать что-то вручную, пользователь
обращается к руководству и находит в нем способ выполнить свою задачу
максимально быстро и с минимальными затратами ручного труда. Однако
если пользователя не устраивает такой принцип работы (когда нужно
часто читать документацию и думать, как организовать так, чтобы
"ручную" работу выполнял компьютер), Vim и Emacs будут не самым
лучшим выбором. Для обычного редактирования текста вручную лучше
выбрать один из текстовых редакторов с простым и привычным
интерфейсом: в дистрибутивах Linux можно найти огромное количество
таких текстовых редакторов с большими или меньшими возможностями: mcedit, joe, pico (часть почтовой программы pine ) – всех не
перечислить. Есть редакторы, которые предназначены для работы не в
терминале, а в графической среде (например, nedit ), у тех же Vim и
Emacs есть графические варианты (GVim и Emacs-X11 или XEmacs), в
которых доступны дополнительные возможности графического
пользовательского интерфейса: меню, иконки и пр.
Задача текстовых редакторов
После основных утилит для работы с файлами и текстом первая
программа, которая понадобится любому пользователю Linux – это текстовый редактор (для краткости – просто редактор). Из предыдущих
лекций и собственных экспериментов Мефодию уже стало понятно, какое
значительное место занимают в системе Linux данные в текстовом
формате, т. е. состоящие из символов, которые могут быть отображены
на экране терминала и которые может прочесть человек. Однако пока
Мефодий мог работать с текстом только последовательно, строка за
строкой; даже имея дело с файлом, он не мог вернуться и
отредактировать уже переданные системе строки. Именно для того, чтобы
работать с текстовым файлом как со страницей, по которой можно
перемещаться и редактировать текст в любой точке, и нужны текстовые
редакторы. Эта кажущаяся сегодня тривиальной возможность сколько угодно редактировать текст,
не оставляя при этом никаких следов, была радикальнейшим достижением прогресса по
сравнению с пишущей машинкой.
Текстовый редактор потребуется пользователю Linux в первую очередь
для того, чтобы изменить настройки системы или своего окружения,
например, shell – при этом нужно будет редактировать конфигурационные
файлы, которые всегда представлены в текстовом формате (см. лекции 8
и 12). Но и собственные задачи пользователя могут потребовать
редактирования текстовых файлов: например, сценарии и программы,
электронные письма, а также заметки для себя, которые пишет Мефодий
—все это данные в текстовом формате. Текстовые данные, полученные при
помощи стандартных утилит, тоже бывает удобно сохранять в файлах и
редактировать.
Не стоит путать текстовые редакторы и текстовые процессоры. Текстовые
процессоры, например OpenOffice Writer или Microsoft Word,
предназначены для создания документов, в которых, помимо собственно
текста, содержится и различная метаинформация (информация об
оформлении): размещение текста на странице, шрифт и т. п. Поскольку в текстовом формате не предусмотрено средств для сохранения информации
об оформлении (там есть только символы и строки), текстовые
процессоры используют собственные форматы для хранения данных. Текст,
в котором нет никакой метаинформации об оформлении, называют "plain
text" (только текст, "плоский", простой текст).
Однако при помощи текстовых редакторов можно работать не только с
форматом plain text. Различная метаинформация (об оформлении, способе
использования текста, например, в качестве ссылки и пр.) может быть
записана и в виде обычных символов (т. е. в текстовом формате ), но со
специальным соглашением, что эти символы нужно интерпретировать
особым образом: как инструкции по обработке текста, а не как текст.
Такие инструкции называются разметкой. Таким образом устроен,
например, формат HTML. Для того чтобы обработать разметку HTML и в
соответствии с ней отобразить текст, нужна специальная программа –
браузер, но редактировать файлы HTML и прочие форматы разметки можно
и при помощи текстового редактора. Кроме того, программы на любых
языках программирования и сценарии (программы на shell) тоже
представляют собой текстовые файлы. Многие текстовые редакторы
ориентированы на работу не только с "плоским" текстом, но и с текстом
в различных форматах. Для этого придумана масса усовершенствований,
уменьшающих количество символов, которые нужно вводить вручную:
специальные команды, клавиатурные сокращения и автодополнение
ключевых слов и конструкций.
Важнейшее условие для текстового редактора в Linux – возможность
работать в терминале, так как это основной способ управления
системой. Поэтому и ввод данных, и редактирование должны полностью
осуществляться средствами терминала, т. е. алфавитно-цифровыми и
некоторыми функциональными клавишами. Поскольку функциональных
клавиш, на которые можно рассчитывать на любом терминале, совсем
немного, а команд, которые нужно отдавать редактору, – очень много,
требуется способ вводить любые команды ограниченными средствами
терминала. Это условие, равно как и требование удобства при работе с
разнообразными структурированными текстами, выполнено в двух
"главных" текстовых редакторах Linux – Vi и Emacs, о которых в
основном и будет идти речь в этой лекции.
Vi и лучше, чем Vi
В любой системе Linux, даже при самой минимальной конфигурации,
всегда присутствует текстовый редактор, поскольку в любой – даже
самой катастрофической – ситуации у пользователя должна быть
возможность отредактировать конфигурационные файлы, чтобы привести
систему в рабочее состояние. По сложившейся традиции текстовым
редактором, который обязательно запустится из любой командной строки
Linux, является ViКак и большинство основных утилит и принципов, унаследованных Linux от UNIX.
Название Vi происходит от visual editor, "визуальный", экранный редактор, поскольку Vi –
первый редактор для UNIX, использующий весь экран для отображения текста и
позволяющий работать с текстом не построчно, а перемещаясь по нему в любых направлениях,
как по странице.. Однако верно и обратное: если вы работаете в
незнакомой системе Linux или произошел сбой, в результате которого
доступна только очень небольшая часть системы, нельзя быть уверенным,
что найдется хоть какой-нибудь другой текстовый редактор, кроме Vi.
Поэтому каждому пользователю Linux нужны хотя бы основные навыки
работы в Vi. При первом знакомстве c Vi работа обычно не ладится:
очень уж он непривычен, его нельзя с удобством использовать, запомнив
только две-три простейшие команды редактирования. Cтоит понять
основные принципы работы в Vi и потратить некоторое время на его
освоение, тогда в нем откроется мощный инструмент, позволяющий очень
эффективно работать с текстом.
Под именем Vi, на самом деле, может скрываться несколько разных
программ: с момента появления Vim в операционной системе UNIX (а это
произошло около 30 лет назад) этот редактор стал чем-то вроде
стандарта. К настоящему времени существует ряд программ, либо в
точности повторяющих вид и поведение "классического" Vi (например, nvi ), либо очень похожих на него, но со значительно расширенными
возможностями (Vim, elvis ). Наибольшей популярностью пользуется Vim,
возможности которого огромны – для их описания потребовалось почти
сто тысяч строк документации. Когда пользователь Linux набирает в
командной строке Vim, скорее всего, будет запущена "облегченная"
версия Vi, которая настроена таким образом, чтобы максимально
воспроизводить поведение классического редактора Vim. Естественно, в
таком режиме часть возможностей Vi недоступна. Все свойства,
которыми Vi отличается от Vim, обязательно снабжены в руководстве по
Vi указанием "not in vi". В дальнейшем изложении под Vi мы будем
понимать именно Vim в режиме совместимости, все возможности,
недоступные в этом режиме, будут оговариваться. Чтобы вызвать Vim в
полнофункциональном режиме, достаточно набрать команду Vim.
Популярность Vi не случайна: этот текстовый редактор позволяет не
только производить простые операции редактирования текстовых файлов –
он хорошо приспособлен и для максимально быстрого и эффективного
решения ряда смежных с редактированием задач. Среди самых важных его
возможностей – инструменты для работы с текстами на различных языках
программирования и в различных форматах разметки. Vim умеет
подсвечивать разными цветами синтаксические конструкции языка
программирования или разметки Обычно современные терминалы и программы-эмуляторы терминалов поддерживают
вывод текста по крайней мере несколькими разными цветами., автоматически выставлять отступы, что
облегчает восприятие структуры документа. Кроме того, в Vim есть
специальные средства для организации цикла отладки программы:
компиляция–правка исходного текста–компиляция... Подробнее об этих и
прочих возможностях Vim можно узнать из руководств по Vim. Объем
данной лекции позволяет описать только самое начало работы с Vi.
Запуск Vi
Чтобы начать сеанс редактирования в Vi, достаточно выполнить команду
Vi на любом терминале. Чтобы открыть для редактирования уже
существующий файл, путь к этому файлу нужно указать в качестве
параметра: " vi путь_к_файлу ". Как и всякая уважающая себя программа
UNIX, Vim может быть запущен с множеством модифицирующих его
поведение ключей, которые подробно описаны в руководстве. Вызванный
без параметра, редактор откроет пустой буфер – чистый лист для
создания нового текста. В центре экрана при этом может появиться
краткое приветственное сообщение, где указаны версия программы и
команды для получения помощи и выхода из редактора (что
нетривиально). Однако такое сообщение может и не появиться – это
зависит от версии Vi, установленной в системе.
Для отображения текста и работы с ним Vi использует весь экран
терминала – только последняя строка предназначена для диалога с
пользователем: вывода информационных сообщений и ввода команд. Пока буфер не заполнен текстом, в начале каждой строки экрана отображается
символ " ~ ", обозначающий, что в этом месте буфера нет ничего, даже
пустой строки. Общий вид экрана в начале работы будет примерно такой:
#
~
~
~
~
~
Символ " # " обозначает курсор. На экране терминала умещается больше
строк, но в примерах мы будем для компактности изображать только
необходимый минимум.
Режимы
В Vi проблема разделения команд редактору и вводимого текста решена
при помощи режимов: в командном режиме нажатие на любую клавишу – это
команда редактору, в режиме вставки нажатие на клавишу приводит к
вставке соответствующего символа в редактируемый текст. Поэтому при
работе с Vi пользователю всегда нужно обращать внимание на то, в
каком режиме находится редактор.
Режимы Vi. Состояния редактора Vi, в которых он по-разному обрабатывает нажатия
клавиш. Различают три режима Vi: командный (нажатие любой клавиши
считается командой и немедленно исполняется), вставки (нажатие
клавиши-печатного символа приводит к вставке этого символа в текст) и командной строки (для ввода длинных команд, отображаемых на экране;
ввод завершается Enter ).
Редактор Vi всегда начинает работу в командном режиме. В этом режиме
есть два способа отдавать команды редактору. Во-первых, нажатие
практически на любую клавишу редактор воспринимает как команду. В
Vim, даже в режиме Vi-совместимости, командное значение определено
для всех латинских букв (в верхнем и нижнем регистрах ), цифр, знаков
препинания и большинства других печатных символов. При нажатии на эти
клавиши вводимые команды нигде не отображаются – они просто Не нужно пытаться вводить текст в командном режиме: поскольку у каждой буквы есть
командное значение, результат может быть самым неожиданным!
Во-вторых, у Vi есть своя командная строка: чтобы ее вызвать, нужно
ввести в командном режиме " :". В результате в начале последней строки
экрана появится двоеточие – это приглашение командной строки. Здесь
вводятся более сложные команды Vi, которые включают в себя целые
слова (например, имена файлов), причем текст набираемой команды,
конечно, отображается. Команды передаются Vi клавишей Enter. В
современных версиях Vim с командной строкой можно работать так же,
как и в shell: редактировать ее, достраивать команды клавишей Tab,
пользоваться историей команд.
Главная команда командной строки Vim – вызов подсистемы помощи " :help
Enter ". Двоеточие переводит Vim в режим командной строки, " help " –
собственно команда, Enter передает команду. help можно вызывать с
аргументом: названием команды или настройки Vim. Vim очень хорошо
документирован, поэтому по команде " :help объект " можно получить
информацию о любом свойстве Vim, например, команда " :help i " выведет
сведения о значении клавиши " i " в командном режиме Vi.
Команда " :set имя_настройки " позволяет настраивать Vim прямо в
процессе работы с ним. Например, отдав команду " :set wrap "
пользователь тем самым включает настройку " wrap ", что заставляет
редактор переносить слишком длинные строки, не умещающиеся в ширину
терминала. Выключить эту настройку можно командой " :set nowrap ", так
что концы длинных строк исчезнут за правым краем экрана.
Наконец, чтобы ввести текст, нужно перейти из командного режима в
режим вставки, нажав клавишу " i " (от " i nsert" – "вставка"). В этот
момент в последней строке появится сообщение о том, что редактор
находится в режиме вставки: " Если используется не Vim, или настройка showmode по умолчанию запрещена,
сообщения может и не быть., в
зависимости от установленного языка системных сообщений.
В режиме вставки можно вводить текст, завершая строку нажатием Enter.
Однако нужно помнить, что в некоторых (ортодоксальных) версиях Vi в
режиме ввода не работают никакие команды перемещения по тексту –
здесь можно только набирать. Если вы заметили, что ошиблись в наборе
– не нужно сразу перемещать курсор и пытаться исправить ошибку:
гораздо удобнее будет внести все исправления потом, в командном
режиме, где доступно множество специальных команд быстрого
перемещения и замены текста. Чтобы перейти из режима вставки обратно
в командный режим, нужно нажать Если Vim пришел в непонятное для вас состояние, нажмите ESC, чтобы вернуться в
командный режим (иногда требуется нажать ESC дважды).
Мефодий начал упражняться с Vim на файле примеров:
methody@oblomov:~ $ vi textfile
Это файл для примеров.
Пример 1.
~
~
~
~
~
"textfile" 2L, 33C 1,1 Весь
Vim начал работу, как и положено – в командном режиме. В последней
строке содержатся некоторые полезные сведения об открытом файле: его
имя, общее количество строк (" 2L "), символов (" 33С "), позиция курсора
(" 1,1 " – номер_строки,номер_символа). " Весь " обозначает, что все
содержимое файла уместилось на экране терминала. Теперь Мефодий
нажмет " i " и введет немного текста:
Это файл для примеров.
Пример 1.
Моя первая строка в vi!
~
~
~
~
-- ВСТАВКА -- 3,24 Весь
Теперь Vim работает в режиме вставки: в последней строке появилось
информационное сообщение об этом. Набрав текст, Мефодий может
вернуться в командный режим, нажав ESC (подсказка " --ВСТАВКА-- " при
этом исчезнет из последней строки).
На самом деле, из командного режима можно перейти в режим ввода
несколькими командами. Разница между ними заключается в том, в какой точке начнется ввод символов. Например, по командам " O " и " o "
(" o pen") можно вводить текст с новой строки (до или после текущей),
по команде " I " – с начала строки, команды " a " и " A " (" a ppend") ведают добавлением символов (после курсора или в конец строки) и т. п.
Работа с файлами
Редактируя текст в Vi, пользователь работает не непосредственно с
файлом, а с буфером. Если открывается уже существующий файл, Vi
копирует его содержимое в буфер и отображает буфер на экране. Все
изменения, которые производит пользователь, происходят именно в
содержимом буфера – открытый файл пока остается неизменным. Если же
Vi вызван без параметра, то создается пустой буфер, который пока не
связан ни с каким файлом В действительности содержимое буфера хранится в специальном временном файле (swap
file). Если сеанс работы в редакторе по какой-то причине прервался, то этот временный
файл не будет удален, и при следующей попытке продолжить незаконченную работу с
файлом Vi предложит провести процедуру восстановления – на случай, если во временном
файле остались несохраненные изменения..
Чтобы записать сделанные изменения в файл, используется команда
" :wEnter " (чтобы ее отдать, нужно сначала перейти в командный режим).
О том, что " w " – это сокращение от англ. " w rite", "записать", можно
узнать, нажав Tab после " :w " – и Vim дополнит эту команду до " write ".
Подобным образом можно поступить с большинством команд в командной
строке Vim – в этом редакторе очень последовательно соблюдается
принцип аббревиативности. Мефодий выполнил " write " и получил такое
информационное сообщение:
Это файл для примеров.
Пример 1.
Моя первая строка в vi!
~
~
~
~
"textfile" 3L, 57C записано 3,24 Весь
Мефодий не указал, куда именно записать содержимое буфера, и по
умолчанию оно было записано в тот файл, который он и открывал для
редактирования: " textfile ". Однако команде " write " можно указать
любое имя файла в качестве параметра – и тогда содержимое буфера
будет записано в этот файл, а если такого файла нет, то он будет
создан. Параметр " write " обязательно потребуется, если текст в буфере
еще не записан ни в каком файле.
Наиболее важна для новичка команда выхода из Vi – " :qEnter "
(сокращение от " q uit"). Пользователь, запустивший редактор в первый
раз, нередко сталкивается с тем, что никак не может его закрыть: не
работает ни один из привычных способов завершения программы, даже
" ^C " Vi обрабатывает по-своему*. И " :w ", и " :q " – команды режима
командной строки; в этот режим Vi переводится из командного режима с
помощью " :", набираемого в начале команды.
Однако если в буфере есть изменения, которые еще не записаны ни в
каком файле, то Vi откажется выполнять команду " :q ", предложив
сначала сохранить эти изменения. Если вы не хотите сохранять
изменения, нужно настоять на своем желании выйти из Vi, добавив к
команде выхода восклицательный знак: " :q!". В этом случае все
несохраненные изменения будут выброшены. Восклицательный знак можно
добавить в конце любой файловой команды в командной строке Vi – в
этом случае Vi будет без возражений выполнять команды.
В Vi предпринято множество усилий для экономии сил и времени
пользователя, командующего редактором. Поэтому можно одним разом
записать текст и выйти из редактора: командой " :wq " или аналогичной
командой " :x ", просто нажав " ZZ " в командном режиме.
Перемещение по тексту
При редактировании в тексте всегда есть точка, в которой пользователь
"находится" в данный момент: вводимые с клавиатуры символы появятся
именно здесь, удаляться символы будут тоже отсюда, к этой точке будут
применяться команды редактора и т. п. Обычно эта точка обозначается
курсором, а в последней (информационной) строке экрана Vim указывает
номера текущей строки и колонки (номер символа в строке), в которых
находится курсор.
Для того чтобы выполнять редактирование текста, по нему необходимо
перемещаться, т. е. перемещать курсор. Самый очевидный способ это
делать – воспользоваться клавишами со стрелками. Нажатие на одну из
этих клавиш обычно заставляет курсор перемещаться на один символ
влево/вправо или на одну строку вверх/вниз. Трудно придумать более
неэффективный и медленный способ перемещения, если нужно попасть на
другой конец объемного текста, и даже простое перемещение к началу или
концу строки может занять несколько секунд.
Заметим, что в процессе редактирования текста обычно возникает
необходимость перемещаться не в произвольную точку, а в некоторые
ключевые: начало и конец строки, слова, предложения, абзаца,
выражения, заключенного в скобки, целого текста. Особенно это
заметно, если требуется редактировать структурированный текст:
программу (например, сценарий), конфигурационный файл и т. п. В Vi
для каждого такого перемещения предусмотрены специальные команды,
обычно состоящие в нажатии одной клавиши в командном режиме.
Используя их, можно не только нажав одну кнопку переместиться на любое
расстояние в тексте, но и двигаться по структурным элементам,
переходя к предыдущему/следующему слову, предложению, абзацу, скобке
и т. д. Прежде чем начинать экспериментировать с перемещением, нужно перейти в командный
режим.
Итак, передвинуть курсор на начало текущей строки можно командой " 0 ",
на первый непробельный символ в строке – " Символами " ^ " и " $ " в Linux повсеместно обозначаются начало и конец строки, в
частности, в регулярных выражениях .
Абзацами Vi считает фрагменты текста, разделенные пустой строкой, к
началу предыдущего/следующего абзаца можно попасть командами " { " и " } "
соответственно. Очень распространенная задача – необходимость попасть
в самый конец файла: для этого служит команда " G " (" G o"), в самое
начало – " gg ".
Передвинуть курсор вперед на начало следующего слова можно командой
" w " (от "word", слово), на начало предыдущего – " b " (от " b ackward",
назад). К началу предыдущего/следующего предложений можно
переместиться командами " ( " и " ) " соответственно. Нужно учитывать,
что границы слов и предложений Vi находит по формальным признакам
(руководствуясь специально определенными регулярными выражениями ),
поэтому решение Vi может иногда не совпадать с представлениями
пользователя о границах слов и предложений. Однако пользователь
всегда властен изменить соответствующие регулярные выражения,
подробности – в документации по Vim.
В Vim никогда не следует вручную повторять одну и ту же команду: если
нужно перейти на три слова вперед, не следует трижды нажимать " w " –
для повторения команды используется множитель. Множитель – это любое
число, набранное перед командой Vi: команда будет повторена
соответствующее число раз. Например, " 3w " – означает "трижды
переместить курсор на слово вперед", иначе говоря, переместить курсор
на три слова вперед. Обратите внимание, что множители могут
применяться не только с командами перемещения, но и с любыми
командами Vi. Аналогично можно переместить курсор на 10 абзацев
вперед командой " 10} ".
Множитель. Число, предшествующее команде Vim и означающее, что данную команду
следует выполнить указанное число раз.
Не сразу очевидно, что поиск шаблона в тексте (строки или регулярного
выражения ) – это тоже команда перемещения. Как и любое перемещение,
поиск осуществляется в командном режиме: прежде всего, нужно нажать
" / ": в последней строке появится символ " / ". Далее следует ввести
шаблон для поиска – он будет отображаться в этой строке, его можно
редактировать. Обычно Vi настроен таким образом, что шаблон для
поиска интерпретируется как регулярное выражение, где ряд символов
имеет специальное значение, эту настройку можно отключить (" :set
nomagic "). После того, как введен шаблон, следует нажать Enter –
курсор переместится к ближайшему (далее по тексту) совпадению с
шаблоном. Поиск в обратном направлении (к предыдущему совпадению)
следует начинать с команды " ?".
Совсем просто перейти к следующему употреблению в тексте того слова,
на котором стоит курсор: для этого нужно просто нажать " * " в
командном режиме. Аналогичная команда поиска слова в обратном
направлении – " # ". Можно специально отметить в тексте точку и затем в
любой момент возвращаться к ней, как к закладке. Одну закладку
определяет сам Vi – " `` ", место в тексте, где было сделано последнее
изменение. Подробно об этих и других командах перемещения можно
прочесть в руководстве по Vim по команде " :help usr_03.txt ".
Изменение текста
В командном режиме нельзя вводить символы в текст с клавиатуры, но
изменить текст при этом можно, например, удаляя символы. Чтобы
удалить отдельный символ (тот, на котором стоит курсор), достаточно
нажать " x " в командном режиме, а чтобы удалить сразу целую строку
(естественно, текущую, то есть ту, в которой находится курсор) –
" dd ". " d " – это сокращение от " d elete", удалить, а " dd " – характерный
прием Vi: удвоение команды означает, что ее нужно применить к текущей
строке.
Из командной строки Vi можно выполнить операцию поиска и замены: для
простой строки или для регулярного выражения. Причем синтаксис
команды поиска и замены полностью воспроизводит синтаксис потокового
редактора sed, о котором уже шла речь в лекции 7:
Это файл для примеров.
Пример 1.
Моя первая строка в vi...
~
~
~
:s/.$/.../
Мефодий хотел заменить в своем файле точки в концах строки
многоточиями. Для этого в командном режиме он нажал " :" (вызов
командной строки Vi), где набрал команду " s " (сокращение от
"substitute", заменить), за которой следует уже знакомое по "sed"
выражение " /что_заменить/на_что_заменить/ ". Только результат
получился совсем не тот, какого ожидал Мефодий: заменился на
многоточие восклицательный знак последней строки. Не учел он
следующего: по умолчанию шаблоны для поиска и замены – это регулярные
выражения, то есть " ." означает вовсе не точку, а "любой символ".
Имея в виду точку, следовало написать " \.". " $ ", как и ожидал
Мефодий, это конец строки. В момент выполнения команды поиска курсор
находился в последней строке, в первом совпадении после курсора и
была произведена замена.
Форматирование текста – это расстановка символов конца строки,
пробелов и табуляций таким образом, чтобы текст хорошо смотрелся на
экране терминала. Форматирование вручную крайне неэффективно. В Vim
автоматическое форматирование текста (если редактируется программа на
каком-либо языке программирования, то с учетом правил этого языка)
может происходить прямо в режиме вставки, в режиме вставки же можно
изменять отступ текущей строки (по командам " ^D " и " ^T "). Для
выравнивания текста по центру, правому или левому краю команды
" :center ", " :left " и " :right " соответственно. Эти команды, как и
большинство команд командной строки, можно применять к диапазону
строк способом, описанным ниже.
Режим ввода не богат специальными командами изменения текста, что и
понятно: он предназначен для ввода. Однако в Vim (но не в Vi!) есть
некоторые удобства, упрощающие и сам процесс набора. Если слово,
которое нужно ввести, уже встречалось в тексте, можно набрать только
первые буквы и нажать " ^P " (" p revious") – Vim попробует сам завершить
его. Если Vim не угадал и предложил не то слово, можно продолжить
перебирать варианты. Команда " ^N " (" n ext") подставляет слова, которые
встречаются ниже по тексту. Подробнее об этой функции можно узнать из
руководства по команде " :help ins-completion ".
Иногда пользователь, изменив текст, тут же хочет вернуть все обратно.
Для этого в Vi предусмотрена команда отмены последнего изменения: " u "
в командном режиме (от " u ndo", отменить). Каким бы сложным,
масштабным (и разрушительным) ни было изменение, совершенное
последней командой, " u " вернет текст в исходное состояние. Впрочем,
саму отмену тоже можно отменить. В классическом Vi доступна отмена
только последней выполненной команды, а в Vim отменить можно сколько
угодно последних команд, а также повторить их командой " ^R ".
Работа с фрагментами текста
Любая команда перемещения определяет две точки в тексте: ту, в
которой был курсор до перемещения, и ту, в которую он переместился в
результате данной команды. Расположенный между этими двумя точками
отрезок текста однозначно задается командой перемещения. Например,
команда " ) " захватывает текст от текущего положения курсора до начала
следующего предложения. Vi позволяет применить к этому фрагменту любую
команду редактирования – так устроены гнездовые команды. Гнездовая
команда состоит из действия и следующего за ним перемещения.
Перемещение задает фрагмент текста, а действие определяет, что с этим
фрагментом сделать. Например, команда " d) " удалит весь текст от
текущей позиции курсора до начала следующего предложения. Наиболее
полезные действия – " d " (" d elete"), " c " (" c hange"), " > " и " < "
(сдвинуть), " y " (запомнить) и " gq " (отформатировать).
Гнездовая команда. Команда редактора Vi, позволяющая применить указанное действие к
указанному отрезку текста. Отрезок задается стандартной командой
перемещения по тексту.
Очень часто возникает необходимость заменить фрагмент в тексте:
слово, предложение, строку и т. д. Это можно сделать в два действия:
сначала удалить часть текста, затем перейти в режим вставки и
вставить замену. Vi предоставляет возможность упростить эту операцию,
сведя два действия к одному: заменить. Гнездовая команда " c "
предназначена именно для этого. Например, команда " cw " (буквально:
" c hange w ord") заменит текст от курсора до начала следующего слова
(так можно заменить одно слово), " c) " заменит текст от курсора до
начала следующего предложения.
Мефодий не забыл, что команды перемещения можно использовать с множителями, и попробовал заменить сразу три слова в своем файле на
другие: для этого он в командном режиме подогнал курсор в начало
слова "первая" и набрал " c3w " ("заменить фрагмент отсюда до начала
третьего слова", буквально: "change 3 words"). Результат этой команды
выглядел так:
Это файл для примеров.
Пример 1.
Моя #vi...
~
~
~
-- ВСТАВКА -- 3,5 Весь
В примере знак " # " обозначает позицию курсора: как видно, Vi удалил
три слова, попавшие в зону действия команды и сразу перешел в режим
вставки. Мефодию осталось только набрать что-то взамен.
Перестановка частей – типичная задача, возникающая в процессе
редактирования. Для перестановки требуется удалить фрагмент в одном
месте текста и вставить его же в другом. Для решения первой части
задачи в Vi нет специальных средств, потому что любая команда
удаления (" d ", " c ", " x " и др.) сохраняет удаленный текст в
специальном регистре. Для вставки последнего удаленного фрагмента
служит команда " p " в командном режиме (от " p ut", положить). При
помощи этой команды Мефодий может вставить только что удаленные им
командой " c3w " три слова:
Это файл для примеров.
Пример 1.
Моя новая строка для vi...
первая строка в
~
~
4,1 Весь
Для того чтобы скопировать фрагмент текста, служит команда " y " (от
" y ank" – забрать, сдернуть): она не удаляет текст, а просто сохраняет
его в том же регистре, что и команды удаления. Команду " y " можно
использовать в гнездовых командах, например, " y5w " сохранит в регистре фрагмент текста от курсора до начала пятого слова. Вставить
скопированный фрагмент можно все той же командой " p ". Однако таким
способом можно вставлять только текст, удаленный или скопированный последним, для хранения нескольких разных фрагментов текста следует использовать
именованные регистры (см. подробнее в руководстве по Vim).
Для того чтобы применить команду к нескольким строкам текста, не
обязательно подгонять к ним курсор. В командной строке Vi любой
команде может предшествовать указание диапазона в тексте, к которому
следует эту команду применить. Команды с указанием диапазона выглядят
так: " :начало,конец}команда ", где начало и конец – это адреса
начальной и конечной строк диапазона (т. е. фрагмента текста), а команда – это команда режима командной строки, такая как " :w " или
" :r ". Многие команды командного режима (в частности, " d " и " y ")
доступны также и в командной строке. В качестве адреса можно
использовать номера строк в файле (команда " :1,5y " будет означать
"скопировать в регистр строки с первой по пятую"), есть специальные
обозначения для текущей строки (" ."), последней строки (" $ ") и всего
файла (" % "). Указать границу диапазона можно и при помощи шаблона:
граничной будет считаться та строка, в которой обнаружится шаблон.
Последним свойством Мефодий воспользовался, чтобы удалить плоды своих
экспериментов: он выполнил команду " :/Пример 1/,$d " (от строки
" Пример 1 " до конца файла – удалить):
Это файл для примеров.
~
~
~
3 fewer lines
Настройка Vi и Vim
Вид и поведение Vi и Vim можно существенно изменить при помощи
настроек, приспособив редактор именно к своим вкусам и привычкам.
Прямо во время работы редактора можно менять настройки из командной
строки Vi при помощи команды " :set имя_настройки ". Кроме того, можно
сделать настройку постоянной, вписав все нужные значения в конфигурационный файл .vimrc (или .exrc – для Vi) в домашнем каталоге
пользователя. При каждом запуске Vim/Vi читает этот файл и исполняет
все содержащиеся в нем команды. Объем лекции не позволяет подробно
остановиться на настройке Vi, читатель может заняться изучением этого
вопроса сам: все необходимые сведения есть в руководствах. Чтобы
оценить возможности настройки, можно выполнить в Vim (но не в Vi!)
команду " :options ", по которой будет выведен список всех доступных
опций с кратким описанием их смысла.
Лучше, чем Emacs?
Заголовок этого раздела сформулирован таким провокационным образом не
случайно: любому пользователю похожей на UNIX операционной системы (к
таким системам относится и Linux) необходим текстовый редактор. Выбор
очень многих пользователей падает на один из двух наиболее популярных
и, как следствие, наиболее универсальных (реализованных и работающих
везде) текстовых редактора: Vi (или одну из его версий, чаще всего
Vim) и Emacs. Оба эти редактора появились около тридцати лет назад,
но почтенный возраст им на пользу: огромное количество разработчиков по всему миру
все эти годы занималось их отладкой, локализацией и расширением.
Vim и Emacs образуют альтернативную пару не только по исторической
случайности: оба редактора претендуют на роль универсального средства
для работы с текстом на любых естественных и искусственных языках. И
действительно, трудно назвать сравнимый с ними по возможностям текстовый редактор, да еще и настолько нетребовательный к интерфейсу:
и Vim, и Emacs будут работать на любом терминале. Однако ограниченные
возможности интерфейса терминала требуют от программ надежного
способа отделения команд редактора от вводимого текста. В Vi и Emacs
эта задача решена по-разному – отсюда и большая часть различий в
стиле работы с этими редакторами, и традиционный спор приверженцев
этих редакторов о том, какой из них лучше.
Тексты на разных языках
Главное свойство, которое сделало Emacs таким популярным и
многофункциональным редактором – это заложенная в нем с самого начала
принципиальная расширяемость. Emacs почти полностью написан на
специально созданном для него языке программирования Emacs Lisp, и у
любого пользователя есть возможность запрограммировать необходимые именно ему функции и подключить их в качестве модуля к Emacs. При
этом сам Emacs никак изменять не требуется. Сообщество программистов
не замедлило воспользоваться расширяемостью Emacs, и к настоящему
времени важнейшее достоинство этого редактора состоит именно в
свободно распространяемых пакетах расширений, содержащих инструменты
для решения самых разнообразных задач, связанных с редактированием
текста.
Современный Emacs – это не просто текстовый редактор, а
интегрированная среда для работы в системе. Основная идея сообщества
разработчиков и пользователей Emacs состоит в том, что Emacs
позволяет работать с любыми данными, которые могут быть представлены
как текст (в лекции 7 обсуждалось, что таким образом можно
представить очень многое в системе). Естественно, список содержащихся
в каталоге файлов, программа на каком-либо языке программирования или
электронное письмо – это тексты, которые сильно различаются по
структуре и по тому, что от них нужно пользователю. В Emacs для
работы с текстами разного типа используются режимы. Обратите внимание, что в Emacs понятие "режим" имеет совершенно иной смысл, чем в Vi!
Режим Emacs. Комплекс команд и настроек Emacs, предназначенных для работы с
текстом определенной структуры, например содержимым каталога,
программой на Си и. т. п.
Каждый буфер в Emacs находится в одном из основных режимов. Основной
режим – это набор функций и настроек Emacs, приспособленных для
редактирования текста определенного вида. Каждый основной режим
по-своему переопределяет некоторые управляющие символы, так что
наиболее доступными становятся команды, чаще всего именно для работы
с текстом данного типа. Команды, специфичные для текущего основного
режима, обычно начинаются с управляющего символа C-c. Некоторое
представление о возможностях Emacs может дать весьма неполный список
тех текстов, для которых существуют основные режимы:
список файлов в каталоге;
программы на самых разных языках программирования, от Си до самых
экзотических;
тексты в различных форматах разметки: XML, HTML, TeX;
словари;
электронная почта (режим позволяет не только читать и писать
письма, но и отправлять и получать их);
календарь;
дневник и личное расписание;
многое другое.
Когда требуется много и быстро работать с текстом на каком-либо
искусственном языке (языке программирования, разметки и пр.),
возможно, Emacs – это лучший выбор.
Не хуже в Emacs развиты и средства работы с текстами на разных
естественных языках с самыми экзотическими письменностями. Просто для
оценки возможностей Emacs в этой области можно выполнить команду " C-h
h ", по которой будет выведен файл, изображающий приветствие на разных
языках.
Команды Emacs
Если в вашей системе установлен Emacs, то вы можете его запустить,
набрав emacs в командной строке любого терминала. Как и Vim, Emacs
использует весь экран терминала, хотя интерфейс у него более богатый:
вверху экрана находится строка с пунктами меню, под ней – окно для
отображения и редактирования текста, которое заканчивается строкой режима, отображаются сведения о происходящем в окне. В самом низу
экрана – строка минибуфера, используемая для диалога с пользователем,
в частности для отображения и редактирования вводимых команд.
Vi и вслед за ним Vim – это многорежимные редакторы, когда команды
вводятся в одном режиме, а текст – в другом, что позволяет
использовать в качестве командных любые клавиши. В Emacs нет
специального командного режима, но использован тот факт, что с
клавиатуры можно вводить не только печатные, но и некоторые управляющие символы. Для этого используются несколько управляющих
клавиш терминала (прежде всего Ctrl и Alt ), нажатые в сочетании с
различными текстовыми символами. Чтобы ввести такой символ, нужно
нажать управляющую клавишу (например, Ctrl ) и, удерживая ее, нажать
клавишу с одним из печатных символов (например, " x "). Кроме того, в
Emacs используется управляющая клавиша Meta. На тех терминалах, где
она отсутствует, ее функции обычно передаются клавише Alt. На
"настоящих" терминалах обычно не бывает ни Meta, ни Alt ; из клавиатурных модификаторов присутствуют только Ctrl и Shift. Тогда на
помощь приходит старая добрая ESC: нажатие ESC, а после нее –
печатного символа (того же " x ") эквивалентно " Meta x ".
Команд в редакторе Emacs чрезвычайно много, доступных управляющих
символов на всех не хватает, поэтому чтобы вызвать команду Emacs,
обычно требуется ввести ключ, начинающийся с управляющего символа, за
которым следует комбинация из управляющих или обычных символов,
просто полное имя команды. Последовательность символов, достаточная
для вызова команды, называется законченным ключом, а если введенных
символов недостаточно для однозначного определения команды, это – префиксный ключ .
Общее правило здесь таково: чем чаще встречается команда, тем короче вызывающий
ее ключ, и наоборот. Для лаконичной записи длинных клавиатурных
комбинаций в сообществе пользователей Emacs сложилась особая традиция
сокращенных обозначений. Клавишу Ctrl обозначают заглавной буквой
" За свои длинные команды из разных комбинаций управляющих клавиш название Emacs
получило шуточную расшифровку: Escape-Meta-Alt-Control-Shift.. Сочетания с командной клавишей обозначаются
дефисом, например, запись С-h обозначает, что нужно, удерживая Ctrl,
нажать " h ". C-h – это префиксный ключ для команд справочной системы
Emacs. Начинающему пользователю стоит выполнить команды " C-h?"
(набрать ?") – справка по командам помощи, " C-h
t " – интерактивный учебник для начинающих пользователей Emacs, и " C-h
i " – полное руководство по Emacs (в формате info ). С ключа C-x
начинаются основные команды Emacs, в частности, для работы с файлами
и буферами. Чтобы завершить работу Emacs, нужно ввести " C-x C-c ".
У любой команды Emacs есть собственное имя. По этому имени можно
вызвать команду, даже если она не привязана ни к какому клавиатурному
ключу. Для вызова команд по имени используется префиксный ключ M-x.
Например, посмотреть справку о помощи в Emacs можно командой " M-x
help-for-help ".
Работа с файлами
В Emacs, как и в Vim, пользователь редактирует текст не в самом файле,
а в буфере. Отличие Emacs в том, что нельзя написать "безымянный"
текст и затем сохранить его в файле. При запуске Emacs без параметров
открывается специальный буфер – " *scratch* ". Он предназначен для
временных заметок – его содержимое будет выброшено при закрытии
Emacs. Если нужно создать новый файл – его следует открыть командой
" C-x C-f ", точно так же открывается для редактирования уже
существующий файл.
После того как Мефодий нажал " C-x C-f ", в минибуфере возникло
приглашение: " Find file: ~/ ". Теперь нужно ввести путь к файлу,
начиная с текущего каталога (Emacs любезно подсказал его Мефодию). С
текстом в минибуфере можно обращаться почти так же, как с командной
строкой shell или Vim: редактировать, использовать автодополнение
(клавишей Tab ), перемещаться по истории стрелочками вверх/вниз.
Мефодий не замедлил воспользоваться этой возможностью и, набрав " te ",
нажав Tab и Enter, приступил к редактированию того же " textfile ".
Сохранить сделанные изменения можно командой " C-x C-s ".
Когда Мефодий захотел открыть еще один буфер, чтобы выполнить один из своих
сценариев, он забыл точное название нужного файла и, набрав " C-x C-f
bin/ ", нажал Enter. В окне возник список файлов в подкаталоге
" ~/bin ", похожий на вывод ls -l:
File Edit Options Buffers Tools Operate Mark Regexp Immediate Subdir Help
/home/methody/bin:
итого 24
drwxr-xr-x 2 methody methody 4096 Дек 2 15:21 .
drwx------ 10 methody methody 4096 Дек 2 15:21 ..
-rwxr-xr-x 1 methody methody 26 Ноя 9 21:34 loop
-rwxr-xr-x 1 methody methody 23 Ноя 9 21:34 script
-rwxr-xr-x 1 methody methody 32 Ноя 9 21:34 to.sort
-rwxr-xr-x 1 methody methody 44 Ноя 9 21:34 two
-RRR:%%-F1 bin (Dired by name)--L5--C51--All--Reading directory /home/methody/bin/...done
Как указано в строке режима, это Dired, редактор каталогов, режим
Emacs, предназначенный для просмотра и изменения каталогов прямо из
редактора. В Dired можно выбирать отдельные файлы или группы файлов и
производить над ними различные действия: открыть для редактирования,
удалить, скопировать, переместить, переименовать по определенной схеме
и т. д. Одним словом, Dired – довольно мощное средство для наглядной
работы с файловой системой, особенно он удобен для работы с группой
файлов. Подробности о командах, доступных в этом режиме, можно найти
в руководстве по Emacs.
Перемещение по тексту
В Emacs, как и в Vim, есть понятие " точка " – то место в буфере, где
будет происходить вставка или удаление данных. Перемещение по тексту
– это перемещение точки. Команды перемещения по структурным элементам
текста развиты не менее, чем в Vim – помимо обычных стрелок,
действуют команды перемещения в начало и конец строки ( C-a и C-e ), буфера ( M-< и M-> ), предложения ( M-a и M-e ), к предыдущему и
следующему слову ( M-f и M-b ), абзацу ( M-{ и M-} ). Различные основные
режимы предоставляют специализированные команды для перемещения по
структурным элементам текстов на разных языках программирования, разметки и др.
В Emacs несколько видов поиска: существуют отдельные команды для
поиска строки и поиска по регулярному выражению. Если требуется найти
ближайшее употребление конкретного слова, удобнее всего
воспользоваться наращиваемым поиском по команде C-s. Наращиваемый
поиск уже встречался Мефодию: так был устроен поиск по истории команд
в bash. По мере набора первых символов искомой строки Emacs переносит точку к ближайшему подобному сочетанию символов после курсора. Поиск
в обратном направлении (к началу буфера ) осуществляется командой C-r. Наращиваемый поиск можно выполнять по регулярному выражению ( C-M-s ).
Все виды наращиваемого поиска в Emacs не различают прописные и
строчные буквы.
Изменение текста
В Emacs есть множество команд, позволяющих пользователю выполнять
меньше действий при редактировании текста. Если пользователь
осознает, что набрал что-то неправильно, он может разом удалить
последнее слово ( M-Del ) или предложение ( C-x Del ). Можно уничтожать и
вперед: до конца слова ( M-d ) и предложения ( M-k ). Emacs хранит не
только последний удаленный фрагмент, но и все предыдущие, формируя список удалений. Только что уничтоженный текст можно вставить
командой C-y. После этого его можно заменить предыдущим уничтоженным
фрагментом – M-y. Можно двигаться и далее назад по списку удалений,
повторяя M-y.
Хорошо продуманы команды для перестановки частей текста вокруг точки:
двух знаков ( C-t ), слов ( M-t ), строк ( C-x C-t ). Команда M-t не
перемещает знаки препинания между словами, поэтому " потеха, дело "
превратится в " дело, потеха ".
Прямо из Emacs можно вызвать программу проверки орфографии (" M-x
ispell-buffer ") или даже включить проверку "на лету", когда
неправильно написанные слова выделяются другим цветом (" M-x
flyspell-mode "). Можно проверить написание отдельного слова, в
котором находится точка (" M-x $ ") или завершить недописанное слово,
основываясь на орфографическом словаре (" M-x Tab ").
В Emacs так много специальных команд для изменения текста, что
команды поиска и замены бывают нужны не так часто. Произвести замену
строки всюду в буфере можно по команде " M-x replace-string что
заменить Enter на_что_заменить Enter ", а для замены регулярного
выражения существует аналогичная команда " M-x replace-regexp ".
Если нужно заменить строку только в некоторых случаях, пригодится
команда M-%, запрашивающая подтверждение о замене при каждой
найденной строке. Аналогичная команда для регулярных выражений – C-M-%.
Любые изменения в тексте можно отменить командой C-_ (нужно нажать Ctrl, Shift и " - ").
Работа с фрагментами текста
Многие команды Emacs работают с произвольным фрагментом текущего буфера. Такие команды всегда применяются к текущей области. Область –
это отрезок текста между точкой (где находится курсор) и меткой. Метка в любой момент присутствует в любом буфере, пользователь может
установить ее в любом месте текста явно – командой M-Пробел. Метка
может перемещаться и без вмешательства пользователя: команды
перемещения и редактирования могут изменять положение метки. Таким
образом, чтобы выделить в буфере фрагмент текста, можно проделать
следующие операции:
переместить точку (курсор) на один конец нужного фрагмента;
нажать M-Пробел (установить метку );
переместить точку к другому концу нужного фрагмента.
Теперь можно выполнять команду редактирования – она будет применена
именно к выделенной области. Например, C-w удалит текст области, а M-w скопирует его. Вставить удаленный или скопированный фрагмент
можно командой C-y.
Есть группа команд, позволяющих работать с меткой более эффективно:
установить метку после конца следующего слова ( M-@ ), пометить текущий
абзац ( M-h ) или весь буфер (" C-x h "). Различные основные режимы
предоставляют команды для пометки структурных элементов текста,
например, разделов документа, определения функции (в тексте
программы) и т. п. Все положения метки хранятся в списке пометок,
перенести точку в любое из предшествующих положений метки можно,
нужное количество раз повторив команду " C-u C-@ ".
Область. Непрерывный отрезок текста, ограниченный точкой с одной стороны и меткой с другой.
Как и в Vim, в Emacs можно использовать для хранения информации регистры. В регистре Emacs можно сохранить позицию в буфере и затем
перейти к этой позиции (" C-x r Пробел x " записывает позицию точки в регистр " x ", а " C-x r j x " переходит в эту позицию). В регистре можно
сохранить текст из области (" C-x r s x " сохраняет область в регистре
" x ", " C-x r i x " – вставляет текст из этого регистра ). В регистрах
также можно хранить числа, имена файлов, конфигурацию окон.
Подробности, как всегда, в руководстве.
Настройка Emacs
Коротко говоря, в Emacs можно настроить все: связи между ключами и
командами редактора, определить макрокоманды, написать собственные
расширения. Есть возможность изменять настройки Emacs как в процессе
работы, так и при помощи конфигурационного файла .emacsrc.
Просто текстовые редакторы
И в Vim, и в Emacs интегрировано множество средств для автоматизации
процесса редактирования. Эти редакторы становятся удобны в том
случае, если прежде чем делать что-то вручную, пользователь
обращается к руководству и находит в нем способ выполнить свою задачу
максимально быстро и с минимальными затратами ручного труда. Однако
если пользователя не устраивает такой принцип работы (когда нужно
часто читать документацию и думать, как организовать так, чтобы
"ручную" работу выполнял компьютер), Vim и Emacs будут не самым
лучшим выбором. Для обычного редактирования текста вручную лучше
выбрать один из текстовых редакторов с простым и привычным
интерфейсом: в дистрибутивах Linux можно найти огромное количество
таких текстовых редакторов с большими или меньшими возможностями: mcedit, joe, pico (часть почтовой программы pine ) – всех не
перечислить. Есть редакторы, которые предназначены для работы не в
терминале, а в графической среде (например, nedit ), у тех же Vim и
Emacs есть графические варианты (GVim и Emacs-X11 или XEmacs), в
которых доступны дополнительные возможности графического
пользовательского интерфейса: меню, иконки и пр.