|
From: | Tino Calancha |
Subject: | bug#27584: 26.0.50; alist-get: Add optional arg TESTFN |
Date: | Sun, 9 Jul 2017 23:45:53 +0900 (JST) |
User-agent: | Alpine 2.20 (DEB 67 2015-01-07) |
On Fri, 7 Jul 2017, Stefan Monnier wrote:
+ (declare (compiler-macro + (lambda (_) + `(pcase ,pred + ('eq (assq ,key ,alist)) + ((or 'equal 'nil) (assoc ,key ,alist)) + ((guard (and (macroexp-const-p ,key) (eq ,pred 'eql))) + (if (floatp ,key) + (assoc ,key ,alist) (assq ,key ,alist))) + (_ (assoc-default ,key ,alist ,pred nil 'full))))))This replaces a call to the function with a chunk of code which does `pcase`, which is not what we want: we want the `pcase` to be executed during compilation and if we can't choose which branch to follow, then we just keep the call unchanged (which is why, in my define-inline example, the pcase was outside of `inline-quote`).
Thank you Stefan. After playing a bit with this i'd like to ask you something. I rewrote it as follows: (declare (compiler-macro (lambda (form) (pcase pred (''eq `(assq ,key ,alist)) ((or ''equal 'nil) `(assoc ,key ,alist)) ((and (guard (macroexp-const-p key)) ''eql) (if (floatp key) `(assoc ,key ,alist) `(assq ,key ,alist))) (t form))))) Apparently, it works as a charm: *) For example, if i compile a file with content: ;; -*- lexical-binding: t; -*- (defun run () (assoc-predicate 999 '((1 . "a") (2 . "b")) 'eql)) *) tmp.elc contains, something like: (defalias 'run #[0 "\300\301\236\207" [999 ((1 . "a") (2 . "b"))] 2]) **) But note what happens if the file contains: ;; -*- lexical-binding: t; -*- (defun run () (assoc-predicate (let ((x 999)) x) '((1 . "a") (2 . "b")) 'eql)) **) tmp.elc shows:(defalias 'run #[0 "\300\301\211\262\302\303#\207" [assoc-predicate 999 ((1 . "a") (2 . "b")) eql] 4])
That is, in the pcase fails the condition: (and (guard (macroexp-const-p key)) ''eql) so that the compiler macro doesn't change the form. But we know that: (macroexp-const-p (let ((x 999)) x)) => t So, i would expect to **) compiles to similar code as *). What is wrong with my assumptions?
[Prev in Thread] | Current Thread | [Next in Thread] |