[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Emacs-diffs] master 44eca25: map.el (map-merge*): Use `map-into' at beg
From: |
Stefan Monnier |
Subject: |
[Emacs-diffs] master 44eca25: map.el (map-merge*): Use `map-into' at beginning rather than end |
Date: |
Sat, 18 Jun 2016 04:51:29 +0000 (UTC) |
branch: master
commit 44eca25a4bd1513f08ca380c9f6722c21376ac9f
Author: Stefan Monnier <address@hidden>
Commit: Stefan Monnier <address@hidden>
map.el (map-merge*): Use `map-into' at beginning rather than end
* lisp/emacs-lisp/map.el (map-merge): Use `map-into' for the first map,
and don't use of an intermediate alist.
(map-merge-with): Same, plus use `cl-callf' to try and avoid performing
3 lookups per inner iteration.
---
lisp/emacs-lisp/map.el | 29 ++++++++++++++++++-----------
1 file changed, 18 insertions(+), 11 deletions(-)
diff --git a/lisp/emacs-lisp/map.el b/lisp/emacs-lisp/map.el
index ba15a65..b97d8b1 100644
--- a/lisp/emacs-lisp/map.el
+++ b/lisp/emacs-lisp/map.el
@@ -43,6 +43,7 @@
;;; Code:
(require 'seq)
+(eval-when-compile (require 'cl-lib))
(pcase-defmacro map (&rest args)
"Build a `pcase' pattern matching map elements.
@@ -282,27 +283,33 @@ MAP can be a list, hash-table or array."
"Merge into a map of type TYPE all the key/value pairs in MAPS.
MAP can be a list, hash-table or array."
- (let (result)
+ (let ((result (map-into (pop maps) type)))
(while maps
+ ;; FIXME: When `type' is `list', we get an O(N^2) behavior.
+ ;; For small tables, this is fine, but for large tables, we
+ ;; should probably use a hash-table internally which we convert
+ ;; to an alist in the end.
(map-apply (lambda (key value)
- (setf (map-elt result key) value))
- (pop maps)))
- (map-into result type)))
+ (setf (map-elt result key) value))
+ (pop maps)))
+ result))
(defun map-merge-with (type function &rest maps)
"Merge into a map of type TYPE all the key/value pairs in MAPS.
When two maps contain the same key, call FUNCTION on the two
values and use the value returned by it.
MAP can be a list, hash-table or array."
- (let (result)
+ (let ((result (map-into (pop maps) type))
+ (not-found (cons nil nil)))
(while maps
(map-apply (lambda (key value)
- (setf (map-elt result key)
- (if (map-contains-key result key)
- (funcall function (map-elt result key) value)
- value)))
- (pop maps)))
- (map-into result type)))
+ (cl-callf (lambda (old)
+ (if (eq old not-found)
+ value
+ (funcall function old value)))
+ (map-elt result key not-found)))
+ (pop maps)))
+ result))
(defun map-into (map type)
"Convert the map MAP into a map of type TYPE.
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Emacs-diffs] master 44eca25: map.el (map-merge*): Use `map-into' at beginning rather than end,
Stefan Monnier <=