diff options
| author | Mattias EngdegÄrd | 2019-10-22 17:02:23 +0200 |
|---|---|---|
| committer | Mattias EngdegÄrd | 2019-10-24 10:23:00 +0200 |
| commit | 539d0411bb04e5b3b32cd77ac3b3e4ad364589da (patch) | |
| tree | af648e2b6719faf7dd9a310acdce692a8b11ca6e | |
| parent | b3b74514e98e2fc85c261a1444ce2db0cf23abfc (diff) | |
| download | emacs-539d0411bb04e5b3b32cd77ac3b3e4ad364589da.tar.gz emacs-539d0411bb04e5b3b32cd77ac3b3e4ad364589da.zip | |
rx.el: Refactor user-definition expansion
* lisp/emacs-lisp/rx.el (rx--translate-not): Simplify structure.
* lisp/emacs-lisp/rx.el (rx--expand-def): New.
(rx--translate-symbol, rx--translate-form): Use rx--expand-def.
| -rw-r--r-- | lisp/emacs-lisp/rx.el | 97 |
1 files changed, 56 insertions, 41 deletions
diff --git a/lisp/emacs-lisp/rx.el b/lisp/emacs-lisp/rx.el index 2370948e81b..d7677f14443 100644 --- a/lisp/emacs-lisp/rx.el +++ b/lisp/emacs-lisp/rx.el | |||
| @@ -122,9 +122,27 @@ Each entry is: | |||
| 122 | as the rx form DEF (which can contain members of ARGS).") | 122 | as the rx form DEF (which can contain members of ARGS).") |
| 123 | 123 | ||
| 124 | (defsubst rx--lookup-def (name) | 124 | (defsubst rx--lookup-def (name) |
| 125 | "Current definition of NAME: (DEF) or (ARGS DEF), or nil if none." | ||
| 125 | (or (cdr (assq name rx--local-definitions)) | 126 | (or (cdr (assq name rx--local-definitions)) |
| 126 | (get name 'rx-definition))) | 127 | (get name 'rx-definition))) |
| 127 | 128 | ||
| 129 | (defun rx--expand-def (form) | ||
| 130 | "FORM expanded (once) if a user-defined construct; otherwise nil." | ||
| 131 | (cond ((symbolp form) | ||
| 132 | (let ((def (rx--lookup-def form))) | ||
| 133 | (and def | ||
| 134 | (if (cdr def) | ||
| 135 | (error "Not an `rx' symbol definition: %s" form) | ||
| 136 | (car def))))) | ||
| 137 | ((consp form) | ||
| 138 | (let* ((op (car form)) | ||
| 139 | (def (rx--lookup-def op))) | ||
| 140 | (and def | ||
| 141 | (if (cdr def) | ||
| 142 | (rx--expand-template | ||
| 143 | op (cdr form) (nth 0 def) (nth 1 def)) | ||
| 144 | (error "Not an `rx' form definition: %s" op))))))) | ||
| 145 | |||
| 128 | ;; TODO: Additions to consider: | 146 | ;; TODO: Additions to consider: |
| 129 | ;; - A construct like `or' but without the match order guarantee, | 147 | ;; - A construct like `or' but without the match order guarantee, |
| 130 | ;; maybe `unordered-or'. Useful for composition or generation of | 148 | ;; maybe `unordered-or'. Useful for composition or generation of |
| @@ -155,11 +173,8 @@ Each entry is: | |||
| 155 | ((let ((class (cdr (assq sym rx--char-classes)))) | 173 | ((let ((class (cdr (assq sym rx--char-classes)))) |
| 156 | (and class (cons (list (concat "[[:" (symbol-name class) ":]]")) t)))) | 174 | (and class (cons (list (concat "[[:" (symbol-name class) ":]]")) t)))) |
| 157 | 175 | ||
| 158 | ((let ((definition (rx--lookup-def sym))) | 176 | ((let ((expanded (rx--expand-def sym))) |
| 159 | (and definition | 177 | (and expanded (rx--translate expanded)))) |
| 160 | (if (cdr definition) | ||
| 161 | (error "Not an `rx' symbol definition: %s" sym) | ||
| 162 | (rx--translate (nth 0 definition)))))) | ||
| 163 | 178 | ||
| 164 | ;; For compatibility with old rx. | 179 | ;; For compatibility with old rx. |
| 165 | ((let ((entry (assq sym rx-constituents))) | 180 | ((let ((entry (assq sym rx-constituents))) |
| @@ -446,21 +461,23 @@ If NEGATED, negate the sense (thus making it positive)." | |||
| 446 | (error "rx `not' form takes exactly one argument")) | 461 | (error "rx `not' form takes exactly one argument")) |
| 447 | (let ((arg (car body))) | 462 | (let ((arg (car body))) |
| 448 | (cond | 463 | (cond |
| 449 | ((consp arg) | 464 | ((and (consp arg) |
| 450 | (pcase (car arg) | 465 | (pcase (car arg) |
| 451 | ((or 'any 'in 'char) (rx--translate-any (not negated) (cdr arg))) | 466 | ((or 'any 'in 'char) |
| 452 | ('syntax (rx--translate-syntax (not negated) (cdr arg))) | 467 | (rx--translate-any (not negated) (cdr arg))) |
| 453 | ('category (rx--translate-category (not negated) (cdr arg))) | 468 | ('syntax |
| 454 | ('not (rx--translate-not (not negated) (cdr arg))) | 469 | (rx--translate-syntax (not negated) (cdr arg))) |
| 455 | (_ (error "Illegal argument to rx `not': %S" arg)))) | 470 | ('category |
| 471 | (rx--translate-category (not negated) (cdr arg))) | ||
| 472 | ('not | ||
| 473 | (rx--translate-not (not negated) (cdr arg)))))) | ||
| 474 | ((let ((class (cdr (assq arg rx--char-classes)))) | ||
| 475 | (and class | ||
| 476 | (rx--translate-any (not negated) (list class))))) | ||
| 456 | ((eq arg 'word-boundary) | 477 | ((eq arg 'word-boundary) |
| 457 | (rx--translate-symbol | 478 | (rx--translate-symbol |
| 458 | (if negated 'word-boundary 'not-word-boundary))) | 479 | (if negated 'word-boundary 'not-word-boundary))) |
| 459 | (t | 480 | (t (error "Illegal argument to rx `not': %S" arg))))) |
| 460 | (let ((class (cdr (assq arg rx--char-classes)))) | ||
| 461 | (if class | ||
| 462 | (rx--translate-any (not negated) (list class)) | ||
| 463 | (error "Illegal argument to rx `not': %s" arg))))))) | ||
| 464 | 481 | ||
| 465 | (defun rx--atomic-regexp (item) | 482 | (defun rx--atomic-regexp (item) |
| 466 | "ITEM is (REGEXP . PRECEDENCE); return a regexp of precedence t." | 483 | "ITEM is (REGEXP . PRECEDENCE); return a regexp of precedence t." |
| @@ -874,30 +891,28 @@ can expand to any number of values." | |||
| 874 | ((or 'regexp 'regex) (rx--translate-regexp body)) | 891 | ((or 'regexp 'regex) (rx--translate-regexp body)) |
| 875 | 892 | ||
| 876 | (op | 893 | (op |
| 877 | (unless (symbolp op) | 894 | (cond |
| 878 | (error "Bad rx operator `%S'" op)) | 895 | ((not (symbolp op)) (error "Bad rx operator `%S'" op)) |
| 879 | (let ((definition (rx--lookup-def op))) | 896 | |
| 880 | (if definition | 897 | ((let ((expanded (rx--expand-def form))) |
| 881 | (if (cdr definition) | 898 | (and expanded |
| 882 | (rx--translate | 899 | (rx--translate expanded)))) |
| 883 | (rx--expand-template | 900 | |
| 884 | op body (nth 0 definition) (nth 1 definition))) | 901 | ;; For compatibility with old rx. |
| 885 | (error "Not an `rx' form definition: %s" op)) | 902 | ((let ((entry (assq op rx-constituents))) |
| 886 | 903 | (and (progn | |
| 887 | ;; For compatibility with old rx. | 904 | (while (and entry (not (consp (cdr entry)))) |
| 888 | (let ((entry (assq op rx-constituents))) | 905 | (setq entry |
| 889 | (if (progn | 906 | (if (symbolp (cdr entry)) |
| 890 | (while (and entry (not (consp (cdr entry)))) | 907 | ;; Alias for another entry. |
| 891 | (setq entry | 908 | (assq (cdr entry) rx-constituents) |
| 892 | (if (symbolp (cdr entry)) | 909 | ;; Wrong type, try further down the list. |
| 893 | ;; Alias for another entry. | 910 | (assq (car entry) |
| 894 | (assq (cdr entry) rx-constituents) | 911 | (cdr (memq entry rx-constituents)))))) |
| 895 | ;; Wrong type, try further down the list. | 912 | entry) |
| 896 | (assq (car entry) | 913 | (rx--translate-compat-form (cdr entry) form)))) |
| 897 | (cdr (memq entry rx-constituents)))))) | 914 | |
| 898 | entry) | 915 | (t (error "Unknown rx form `%s'" op))))))) |
| 899 | (rx--translate-compat-form (cdr entry) form) | ||
| 900 | (error "Unknown rx form `%s'" op))))))))) | ||
| 901 | 916 | ||
| 902 | (defconst rx--builtin-forms | 917 | (defconst rx--builtin-forms |
| 903 | '(seq sequence : and or | any in char not-char not | 918 | '(seq sequence : and or | any in char not-char not |