Я пытаюсь обернуть голову вокруг формата font-lock-keywords
Keywords , в частности варианта MATCH-ANCHORED
, но я не вижу, как бы я использовал повторы , сгенерированные из одного регулярного выражения. Ниже моя установка для иллюстрации:
(defvar fmt-font-lock-keywords
;; no-args
`(("~\\(@:?\\|:@?\\)?[]>()}aswvcp;_]"
(0 font-lock-keyword-face))
;; numeric-arg
("~\\([0-9]*\\|#,?\\)\\(@:?\\|:@?\\)?[i*%&|~{[]"
(0 font-lock-keyword-face))
;; decimal
("~\\([0-9]*\\|#\\(,[0-9]*\\|#\\)\\{0,3\\}\\)?\\(@:?\\|:@?\\)?[rdbox]"
(0 font-lock-keyword-face))
;; floating-point f
(,(concat
"~\\(\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{3\\}\\(,'\\w\\)\\{1,2\\}\\)\\|"
"\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{0,3\\}\\)\\)"
"?\\(@:?\\|:@?\\)?f")
(0 font-lock-keyword-face))
;; floating-point e, g
(,(concat
"~\\(\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{3\\}\\(,'\\w\\)\\{1,3\\}\\)\\|"
"\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{0,3\\}\\)\\)"
"?\\(@:?\\|:@?\\)?[eg]")
(0 font-lock-keyword-face))
;; currency
(,(concat
"~\\(\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{2\\}\\(,'\\w\\)\\)\\|"
"\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{0,2\\}\\)\\)"
"?\\(@:?\\|:@?\\)?[$]")
(0 font-lock-keyword-face))
;; tabulation
("~\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)?\\)?\\(@:?\\|:@?\\)?t"
(0 font-lock-keyword-face))
;; escape
("~\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{0,2\\}\\)?\\(@:?\\|:@?\\)?^"
(0 font-lock-keyword-face))
;; logical block
("~\\(\\([0-9]*\\|#\\)\\(,\\([0-9]*\\|#\\)\\)\\{0,3\\}\\)?\\(@:?\\|:@?\\)?<"
(0 font-lock-keyword-face))
;; custom function
(,(concat
"~\\(\\([0-9]+\\|'\\w\\|#\\)\\(,\\([0-9]+\\|'\\w\\|#\\)+\\)*\\)?"
"\\(@:?\\|:@?\\)?\\/[^\\s\\n,#@]+\\/")
(0 font-lock-keyword-face))))
И при инициализации этого режима:
(define-derived-mode fmt-mode fundamental-mode
. . .
(set (make-local-variable 'font-lock-defaults)
'(fmt-font-lock-keywords)) . . .)
Извините, я знаю, что это похоже на клинопись, но на самом деле это очень просто ... это анализ мини-языка формата Common Lisp.
Что он делает сейчас: он окрашивает все специальные подстроки, используя ключевое слово face, но я бы хотел по-разному раскрасить определенные части (числовые аргументы будут окрашены по-разному, вызов пользовательской функции будет окрашен по-разному, at и colon - может по другому, символьные данные - может и по другому тоже).
Я мог бы, технически, продублировать эти регулярные выражения, чтобы извлечь другую группу, но это очень нелегко, кроме того, в случаях, когда возможно передать переменное число аргументов, запись будет близка к комбинаторному взрыву ...
Я понимаю, что анализ может быть решен гораздо проще, если не использовать регулярные выражения, но я не знаю, как совместить его с режимом блокировки шрифтов. Но если вам случится знать, как это сделать без регулярных выражений, и в то же время использовать механику блокировки шрифтов для раскраски, это был бы отличный ответ!