Функции поиска текстовых свойств
При обычном использовании текстовых свойств большинство или многие соседние символы часто имеют одинаковое значение свойства. Вместо того чтобы писать программы, которые проверяют символы по одному, гораздо быстрее обрабатывать фрагменты текста с одинаковым значением свойства.
Вот функции, которые можно использовать для этого. Для сравнения значений свойств они используют eq. Во всех случаях значение object по умолчанию — текущий буфер.
Для хорошей производительности очень важно использовать аргумент limit этих функций, особенно функций, выполняющих поиск по одному свойству: в противном случае они могут долго сканировать буфер до конца, если интересующее вас свойство не меняется.
Эти функции не перемещают точку; вместо этого они возвращают позицию (или nil). Помните, что позиция всегда находится между двумя символами; позиция, возвращаемая этими функциями, находится между символами с различными свойствами.
- Функция: next-property-change pos &optional object limit
-
Функция сканирует текст в строке или буфере object вперёд, начиная с позиции pos, пока не обнаружит изменение какого-либо текстового свойства, после чего возвращает позицию этого изменения. Иными словами, она возвращает позицию первого символа после pos, свойства которого не идентичны свойствам символа сразу после pos.
Если limit не равен
nil, сканирование заканчивается на позиции limit. Если до этой позиции изменений свойств нет, функция возвращает limit.Значение равно
nil, если свойства остаются неизменными до конца object и limit равенnil. Если значение не равноnil, оно представляет собой позицию, большую или равную pos. Значение равно pos только в том случае, если limit равен pos.Вот пример сканирования буфера по фрагментам текста, в пределах которых все свойства постоянны:
(while (not (eobp)) (let ((plist (text-properties-at (point))) (next-change (or (next-property-change (point) (current-buffer)) (point-max)))) Process text from point to next-change... (goto-char next-change)))
- Функция: previous-property-change pos &optional object limit
Эта функция аналогична
next-property-change, но сканирует текст назад от pos, а не вперёд. Если значение не равноnil, оно представляет собой позицию, меньшую или равную pos; оно равно pos только в том случае, если limit равен pos.
- Функция: next-single-property-change pos prop &optional object limit
-
Функция сканирует текст в поисках изменения свойства prop, после чего возвращает позицию этого изменения. Сканирование идёт вперёд от позиции pos в строке или буфере object. Иными словами, эта функция возвращает позицию первого символа после pos, свойство prop которого отличается от свойства символа сразу после pos.
Если limit не равен
nil, сканирование заканчивается на позиции limit. Если до этой позиции изменений свойства нет,next-single-property-changeвозвращает limit.Значение равно
nil, если свойство остаётся неизменным до конца object и limit равенnil. Если значение не равноnil, оно представляет собой позицию, большую или равную pos; оно равно pos только в том случае, если limit равен pos.
- Функция: previous-single-property-change pos prop &optional object limit
Эта функция аналогична
next-single-property-change, но сканирует текст назад от pos, а не вперёд. Если значение не равноnil, оно представляет собой позицию, меньшую или равную pos; оно равно pos только в том случае, если limit равен pos.
- Функция: next-char-property-change pos &optional limit
Эта функция аналогична
next-property-change, за исключением того, что она учитывает как свойства оверлеев, так и текстовые свойства и, если до конца буфера изменения не найдены, возвращает максимальную позицию буфера, а неnil(в этом смысле она похожа на соответствующую функцию для оверлеевnext-overlay-change, а не наnext-property-change). Аргумента object нет, поскольку эта функция работает только с текущим буфером. Она возвращает следующий адрес, в котором изменяется свойство любого из этих типов.
- Функция: previous-char-property-change pos &optional limit
Эта функция аналогична
next-char-property-change, но сканирует текст назад от pos, а не вперёд, и возвращает минимальную позицию буфера, если изменение не найдено.
- Функция: next-single-char-property-change pos prop &optional object limit
Эта функция аналогична
next-single-property-change, за исключением того, что она учитывает как свойства оверлеев, так и текстовые свойства и, если до конца object изменения не найдены, возвращает максимальную допустимую позицию в object, а неnil. В отличие отnext-char-property-change, эта функция имеет аргумент object; если object не является буфером, учитываются только текстовые свойства.
- Функция: previous-single-char-property-change pos prop &optional object limit
Эта функция аналогична
next-single-char-property-change, но сканирует текст назад от pos, а не вперёд, и возвращает минимальную допустимую позицию в object, если изменение не найдено.
- Функция: text-property-any start end prop value &optional object
-
Эта функция возвращает значение, не равное
nil, если хотя бы один символ между start и end имеет свойство prop со значением value. Точнее, она возвращает позицию первого такого символа. В противном случае она возвращаетnil.Необязательный пятый аргумент, object, задаёт строку или буфер для сканирования. Позиции отсчитываются относительно object. По умолчанию object — текущий буфер.
- Функция: text-property-not-all start end prop value &optional object
-
Эта функция возвращает значение, не равное
nil, если хотя бы один символ между start и end не имеет свойства prop со значением value. Точнее, она возвращает позицию первого такого символа. В противном случае она возвращаетnil.Необязательный пятый аргумент, object, задаёт строку или буфер для сканирования. Позиции отсчитываются относительно object. По умолчанию object — текущий буфер.
- Функция: text-property-search-forward prop &optional value predicate not-current
-
Выполняет поиск следующего участка текста, свойство prop которого соответствует value (по умолчанию
nil) согласно predicate.Эта функция устроена по образцу
search-forward(см. раздел Поиск строк) и связанных с ней функций: она перемещает точку, но также возвращает структуру с описанием совпадения, а не возвращает его вmatch-beginningи связанных с ней функциях.Если текстовое свойство с подходящим значением найти не удаётся, функция возвращает
nil. Если оно найдено, точка устанавливается в конец участка с этим текстовым свойством, а функция возвращает структуруprop-matchс информацией о совпадении.predicate может быть равен
t(синонимequal),nil(означает «не равно») или предикатом, который вызывается с двумя аргументами: value и значением текстового свойства prop в позиции буфера, проверяемой на совпадение. При совпадении функция должна возвращать значение, не равноеnil, а в противном случае —nil.Если not-current не равен
nil, а точка уже находится в участке с совпадающим свойством, функция пропускает этот участок и ищет следующий.Структура
prop-matchимеет следующие функции доступа:prop-match-beginning(начало совпадения),prop-match-end(конец совпадения) иprop-match-value(значение property в начале совпадения).В примерах ниже используется буфер со следующим содержимым:
This is a bold and here’s bolditalic and this is the end.
То есть слова, выделенные «жирным шрифтом», используют начертание
bold, а слово, выделенное «курсивом», — начертаниеitalic.Если точка находится в начале:
(while (setq match (text-property-search-forward 'face 'bold t)) (push (buffer-substring (prop-match-beginning match) (prop-match-end match)) words))Этот пример выберет все слова, использующие начертание
bold.(while (setq match (text-property-search-forward 'face nil t)) (push (buffer-substring (prop-match-beginning match) (prop-match-end match)) words))Этот пример выберет все фрагменты без свойств начертания, в результате чего получится список ‘("This is a " "and here's " "and this is the end")’ (только в обратном порядке, поскольку мы использовали
push; см. раздел Изменение переменных-списков).(while (setq match (text-property-search-forward 'face nil nil)) (push (buffer-substring (prop-match-beginning match) (prop-match-end match)) words))Этот пример выберет все участки, в которых для
faceзадано какое-либо значение. Однако результат будет разделён в местах изменения свойств, поэтому в данном случае получится список ‘("bold" "bold" "italic")’.Для более реалистичного примера применения представьте, что у вас есть буфер, в котором некоторые участки представляют URL-адреса и помечены свойством
shr-url.(while (setq match (text-property-search-forward 'shr-url nil nil)) (push (prop-match-value match) urls))
В результате вы получите список всех этих URL-адресов.
- Функция: text-property-search-backward prop &optional value predicate not-current
Эта функция аналогична
text-property-search-forward, но выполняет поиск назад и, если совпадение найдено, устанавливает точку в начало найденного участка, а не в конец.
Copyright © 1990-1996, 1998-2026 Free Software Foundation, Inc.
Licensed under the GNU GPL license.
https://www.gnu.org/software/emacs/manual/html_node/elisp/Property-Search.html