* bug#19814: 24.4; pcase-lambda
@ 2015-02-08 9:01 Leo Liu
2015-02-08 19:18 ` Stefan Monnier
2015-02-09 2:17 ` Leo Liu
0 siblings, 2 replies; 6+ messages in thread
From: Leo Liu @ 2015-02-08 9:01 UTC (permalink / raw)
To: 19814
[-- Attachment #1: Type: text/plain, Size: 140 bytes --]
The attached patch intends to implement pcase-lambda with lambda-list
being a list of positional UPatterns. &rest is supported. Comments?
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: pcase-lambda.diff --]
[-- Type: text/x-patch, Size: 2602 bytes --]
diff --git a/lisp/emacs-lisp/lisp-mode.el b/lisp/emacs-lisp/lisp-mode.el
index 868a9578..5d912097 100644
--- a/lisp/emacs-lisp/lisp-mode.el
+++ b/lisp/emacs-lisp/lisp-mode.el
@@ -204,7 +204,7 @@ (pcase-let
"defface"))
(el-tdefs '("defgroup" "deftheme"))
(el-kw '("while-no-input" "letrec" "pcase" "pcase-exhaustive"
- "pcase-let" "pcase-let*" "save-restriction"
+ "pcase-lambda" "pcase-let" "pcase-let*" "save-restriction"
"save-excursion" "save-selected-window"
;; "eval-after-load" "eval-next-after-load"
"save-window-excursion" "save-current-buffer"
diff --git a/lisp/emacs-lisp/macroexp.el b/lisp/emacs-lisp/macroexp.el
index 797de9ab..8fe156c4 100644
--- a/lisp/emacs-lisp/macroexp.el
+++ b/lisp/emacs-lisp/macroexp.el
@@ -297,6 +297,16 @@ (defun macroexpand-all (form &optional environment)
;;; Handy functions to use in macros.
+(defun macroexp-parse-body (exps)
+ "Parse EXPS into (DOC DECLARE-FORM INTERACTIVE-FORM . BODY)."
+ `(,(and (stringp (car exps))
+ (pop exps))
+ ,(and (eq (car-safe (car exps)) 'declare)
+ (pop exps))
+ ,(and (eq (car-safe (car exps)) 'interactive)
+ (pop exps))
+ ,@exps))
+
(defun macroexp-progn (exps)
"Return an expression equivalent to `(progn ,@EXPS)."
(if (cdr exps) `(progn ,@exps) (car exps)))
diff --git a/lisp/emacs-lisp/pcase.el b/lisp/emacs-lisp/pcase.el
index b495793b..0c71451b 100644
--- a/lisp/emacs-lisp/pcase.el
+++ b/lisp/emacs-lisp/pcase.el
@@ -164,6 +164,23 @@ (defmacro pcase-exhaustive (exp &rest cases)
;; FIXME: Could we add the FILE:LINE data in the error message?
exp (append cases `((,x (error "No clause matching `%S'" ,x)))))))
+;;;###autoload
+(defmacro pcase-lambda (lambda-list &rest body)
+ (declare (doc-string 2) (indent defun))
+ (let ((args (make-symbol "args"))
+ (pats (mapcar (lambda (u)
+ (unless (eq u '&rest)
+ (if (eq (car-safe u) '\`) (cadr u) (list '\, u))))
+ lambda-list))
+ (body (macroexp-parse-body body)))
+ ;; Handle &rest
+ (when (eq nil (car (last pats 2)))
+ (setq pats (append (butlast pats 2) (car (last pats)))))
+ `(lambda (&rest ,args)
+ ,@(remq nil (list (nth 0 body) (nth 1 body) (nth 2 body)))
+ (pcase ,args
+ (,(list '\` pats) . ,(nthcdr 3 body))))))
+
(defun pcase--let* (bindings body)
(cond
((null bindings) (macroexp-progn body))
^ permalink raw reply related [flat|nested] 6+ messages in thread
* bug#19814: 24.4; pcase-lambda
2015-02-08 9:01 bug#19814: 24.4; pcase-lambda Leo Liu
@ 2015-02-08 19:18 ` Stefan Monnier
2015-02-09 1:14 ` Leo Liu
2015-02-09 2:17 ` Leo Liu
1 sibling, 1 reply; 6+ messages in thread
From: Stefan Monnier @ 2015-02-08 19:18 UTC (permalink / raw)
To: Leo Liu; +Cc: 19814
> +(defun macroexp-parse-body (exps)
> + "Parse EXPS into (DOC DECLARE-FORM INTERACTIVE-FORM . BODY)."
> + `(,(and (stringp (car exps))
> + (pop exps))
> + ,(and (eq (car-safe (car exps)) 'declare)
> + (pop exps))
> + ,(and (eq (car-safe (car exps)) 'interactive)
> + (pop exps))
> + ,@exps))
Maybe it'd be better to just splitting the body into 2 parts:
- "declarations", which would include docstrings, `declare's, and interactive
- code.
Stefan
^ permalink raw reply [flat|nested] 6+ messages in thread
* bug#19814: 24.4; pcase-lambda
2015-02-08 19:18 ` Stefan Monnier
@ 2015-02-09 1:14 ` Leo Liu
2015-02-09 4:27 ` Stefan Monnier
0 siblings, 1 reply; 6+ messages in thread
From: Leo Liu @ 2015-02-09 1:14 UTC (permalink / raw)
To: Stefan Monnier; +Cc: 19814
On 2015-02-09 03:18 +0800, Stefan Monnier wrote:
> Maybe it'd be better to just splitting the body into 2 parts:
> - "declarations", which would include docstrings, `declare's, and interactive
> - code.
Coincidentally I have done just that locally :)
(defun macroexp-parse-body (exps)
"Parse EXPS into ((DOC DECLARE-FORM INTERACTIVE-FORM) . BODY)."
`((,(and (stringp (car exps))
(pop exps))
,(and (eq (car-safe (car exps)) 'declare)
(pop exps))
,(and (eq (car-safe (car exps)) 'interactive)
(pop exps)))
,@exps))
Leo
^ permalink raw reply [flat|nested] 6+ messages in thread
* bug#19814: 24.4; pcase-lambda
2015-02-08 9:01 bug#19814: 24.4; pcase-lambda Leo Liu
2015-02-08 19:18 ` Stefan Monnier
@ 2015-02-09 2:17 ` Leo Liu
1 sibling, 0 replies; 6+ messages in thread
From: Leo Liu @ 2015-02-09 2:17 UTC (permalink / raw)
To: 19814-done
Version: 25.1
^ permalink raw reply [flat|nested] 6+ messages in thread
* bug#19814: 24.4; pcase-lambda
2015-02-09 1:14 ` Leo Liu
@ 2015-02-09 4:27 ` Stefan Monnier
2015-02-09 5:30 ` Leo Liu
0 siblings, 1 reply; 6+ messages in thread
From: Stefan Monnier @ 2015-02-09 4:27 UTC (permalink / raw)
To: Leo Liu; +Cc: 19814
>> Maybe it'd be better to just splitting the body into 2 parts:
>> - "declarations", which would include docstrings, `declare's, and interactive
>> - code.
> Coincidentally I have done just that locally :)
> (defun macroexp-parse-body (exps)
> "Parse EXPS into ((DOC DECLARE-FORM INTERACTIVE-FORM) . BODY)."
> `((,(and (stringp (car exps))
> (pop exps))
> ,(and (eq (car-safe (car exps)) 'declare)
> (pop exps))
> ,(and (eq (car-safe (car exps)) 'interactive)
> (pop exps)))
> ,@exps))
No, I meant (DECLS . BODY) such that
(let ((x (macroexp-parse-body body)))
(append (car x) (cdr x)))
return something `equal' to `body'.
Stefan
^ permalink raw reply [flat|nested] 6+ messages in thread
* bug#19814: 24.4; pcase-lambda
2015-02-09 4:27 ` Stefan Monnier
@ 2015-02-09 5:30 ` Leo Liu
0 siblings, 0 replies; 6+ messages in thread
From: Leo Liu @ 2015-02-09 5:30 UTC (permalink / raw)
To: Stefan Monnier; +Cc: 19814
On 2015-02-09 12:27 +0800, Stefan Monnier wrote:
> No, I meant (DECLS . BODY) such that
>
> (let ((x (macroexp-parse-body body)))
> (append (car x) (cdr x)))
>
> return something `equal' to `body'.
Ahh, I see. We can certainly do that.
But isn't the version committed to master slightly more flexible i.e.
one can easily access the individual DOC, DECLARE or INTERACTIVE form?
And if one wants to use the prelude (without the `nil') as a whole it is
just (remq nil (car PARSED-BODY)) away? What do you think?
Leo
^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2015-02-09 5:30 UTC | newest]
Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2015-02-08 9:01 bug#19814: 24.4; pcase-lambda Leo Liu
2015-02-08 19:18 ` Stefan Monnier
2015-02-09 1:14 ` Leo Liu
2015-02-09 4:27 ` Stefan Monnier
2015-02-09 5:30 ` Leo Liu
2015-02-09 2:17 ` Leo Liu
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/emacs.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).