org-cite-list-citations: Cache footnote-definition searches

* lisp/oc.el (org-cite-list-citations): Avoid quadratic complexity.
Pre-calculate list of all footnote definitions and cache the footnote
label search hits.  Do not make `org-element-map' accumulate unused
result.
This commit is contained in:
Ihor Radchenko 2022-06-16 10:43:29 +08:00
parent 37a447ae08
commit b061e7b61c
No known key found for this signature in database
GPG Key ID: 6470762A7DA11D8B
1 changed files with 19 additions and 6 deletions

View File

@ -854,6 +854,8 @@ INFO is the export communication channel, as a property list."
(or (plist-get info :citations)
(letrec ((cites nil)
(tree (plist-get info :parse-tree))
(definition-cache (make-hash-table :test #'equal))
(definition-list nil)
(find-definition
;; Find definition for standard reference LABEL. At
;; this point, it is impossible to rely on
@ -862,11 +864,21 @@ INFO is the export communication channel, as a property list."
;; un-processed citation objects. So we use
;; a simplified version of the function above.
(lambda (label)
(org-element-map tree 'footnote-definition
(lambda (d)
(and (equal label (org-element-property :label d))
(or (org-element-contents d) "")))
info t)))
(or (gethash label definition-cache)
(org-element-map
(or definition-list
(setq definition-list
(org-element-map
tree
'footnote-definition
#'identity info)))
'footnote-definition
(lambda (d)
(and (equal label (org-element-property :label d))
(puthash label
(or (org-element-contents d) "")
definition-cache)))
info t))))
(search-cites
(lambda (data)
(org-element-map data '(citation footnote-reference)
@ -880,7 +892,8 @@ INFO is the export communication channel, as a property list."
(_
(let ((label (org-element-property :label datum)))
(funcall search-cites
(funcall find-definition label))))))
(funcall find-definition label)))))
nil)
info nil 'footnote-definition t))))
(funcall search-cites tree)
(let ((result (nreverse cites)))