ox: Small refactoring

* lisp/ox.el (org-export-get-loc): Refactor code.  Speed-up processing
  when the element doesn't require line numbering.
* testing/lisp/test-ox.el (test-org-gen-loc-list): Reformat code.
This commit is contained in:
Nicolas Goaziou 2016-05-24 21:40:43 +02:00
parent af8e3d84ee
commit 96cfef229d
2 changed files with 115 additions and 66 deletions

View File

@ -4450,40 +4450,34 @@ objects of the same type."
;; code in a format suitable for plain text or verbatim output.
(defun org-export-get-loc (element info)
"Return accumulated lines of code up to ELEMENT.
"Return count of lines of code before ELEMENT.
INFO is the plist used as a communication channel.
ELEMENT is an example-block or src-block element. INFO is the
plist used as a communication channel.
ELEMENT is excluded from count."
(let ((loc 0)
(linum (org-element-property :number-lines element)))
(org-element-map (plist-get info :parse-tree)
`(src-block example-block ,(org-element-type element))
(lambda (el)
(cond
;; ELEMENT is reached: Quit the loop.
((eq el element))
;; Only count lines from src-block and example-block elements
;; with a "+n" or "-n" switch. A "-n" switch resets counter.
((not (memq (org-element-type el) '(src-block example-block))) nil)
((let ((linums (org-element-property :number-lines el)))
(when linums
;; Accumulate locs or reset them.
(let ((lines (org-count-lines
(org-trim (org-element-property :value el)))))
(if (eq (car linums) 'new)
(setq loc 0))
(setq loc (+ loc lines (cdr linums))))))
;; Return nil to stay in the loop.
nil)))
info 'first-match)
;; Add the offset from [+-]n to the loc for the final starting
;; number of lines before the first starting line.
(setq loc (cl-case (car linum)
(continued (+ (cdr linum) loc))
(new (cdr linum))))
;; Return value.
loc))
Count includes every line of code in example-block or src-block
with a \"+n\" or \"-n\" switch before block. Return nil if
ELEMENT doesn't allow line numbering."
(pcase (org-element-property :number-lines element)
(`(new . ,n) n)
(`(continued . ,n)
(let ((loc 0))
(org-element-map (plist-get info :parse-tree) '(src-block example-block)
(lambda (el)
;; ELEMENT is reached: Quit loop and return locs.
(if (eq el element) (+ loc n)
;; Only count lines from src-block and example-block
;; elements with a "+n" or "-n" switch.
(let ((linum (org-element-property :number-lines el)))
(when linum
(let ((lines (org-count-lines
(org-trim (org-element-property :value el)))))
;; Accumulate locs or reset them.
(pcase linum
(`(new . ,n) (setq loc (+ n lines)))
(`(continued . ,n) (cl-incf loc (+ n lines)))))))
nil)) ;Return nil to stay in the loop.
info 'first-match)))))
(defun org-export-unravel-code (element)
"Clean source code and extract references out of it.

View File

@ -2587,68 +2587,123 @@ Paragraph[fn:1][fn:2][fn:lbl3:C<<target>>][[test]][[target]]
info t))))
(defun test-org-gen-loc-list(text type)
(org-test-with-parsed-data text
(org-element-map tree type
(lambda(el) (or (org-export-get-loc el info) "nil")))))
(org-test-with-parsed-data text
(org-element-map tree type
(lambda (el) (or (org-export-get-loc el info) 'no-loc)))))
(ert-deftest test-org-export/get-loc ()
"Test `org-export-get-loc' specifications."
(should
;; "-n" resets line number.
(equal '(0)
(test-org-gen-loc-list "#+BEGIN_EXAMPLE -n\n Text\n#+END_EXAMPLE" 'example-block)))
(test-org-gen-loc-list "#+BEGIN_EXAMPLE -n\n Text\n#+END_EXAMPLE"
'example-block)))
;; The first "+n" has 0 lines before it
(should
(equal '(0)
(test-org-gen-loc-list "#+BEGIN_EXAMPLE +n\n Text\n#+END_EXAMPLE" 'example-block)))
(test-org-gen-loc-list "#+BEGIN_EXAMPLE +n\n Text\n#+END_EXAMPLE"
'example-block)))
;; "-n 10" resets line number but has "9 lines" before it.
(should
(equal '(9)
(test-org-gen-loc-list "#+BEGIN_EXAMPLE -n 10\n Text\n#+END_EXAMPLE" 'example-block)))
(test-org-gen-loc-list "#+BEGIN_EXAMPLE -n 10\n Text\n#+END_EXAMPLE"
'example-block)))
;; -n10 with two lines then +n 15
(should
(equal '(9 25)
(test-org-gen-loc-list "#+BEGIN_EXAMPLE -n 10\n Text_10\n Second line(11)\n#+END_EXAMPLE
#+BEGIN_EXAMPLE +n 15\n Text line (11 + 15)\n#+END_EXAMPLE" 'example-block)))
(test-org-gen-loc-list "
#+BEGIN_EXAMPLE -n 10
Text_10
Second line(11)
#+END_EXAMPLE
#+BEGIN_EXAMPLE +n 15
Text line (11 + 15)
#+END_EXAMPLE"
'example-block)))
(should
(equal '(9 19 0)
(test-org-gen-loc-list "#+BEGIN_EXAMPLE -n 10\n Text\n#+END_EXAMPLE
#+BEGIN_EXAMPLE +n 10\n Text \n#+END_EXAMPLE\n
#+BEGIN_EXAMPLE -n\n Text \n#+END_EXAMPLE" 'example-block)))
(test-org-gen-loc-list "
#+BEGIN_EXAMPLE -n 10
Text
#+END_EXAMPLE
#+BEGIN_EXAMPLE +n 10
Text
#+END_EXAMPLE
#+BEGIN_EXAMPLE -n
Text
#+END_EXAMPLE"
'example-block)))
;; an Example Block without -n does not add to the line count.
(should
;; an Example Block without -n does not add to the line count
(equal '(9 "nil" 19)
(test-org-gen-loc-list "#+BEGIN_EXAMPLE -n 10\n Text\n#+END_EXAMPLE
#+BEGIN_EXAMPLE\n Text\n#+END_EXAMPLE
#+BEGIN_EXAMPLE +n 10\n Text\n#+END_EXAMPLE" 'example-block)))
(equal '(9 no-loc 19)
(test-org-gen-loc-list "
#+BEGIN_EXAMPLE -n 10
Text
#+END_EXAMPLE
#+BEGIN_EXAMPLE
Text
#+END_EXAMPLE
#+BEGIN_EXAMPLE +n 10
Text
#+END_EXAMPLE"
'example-block)))
;; "-n" resets line number.
(should
(equal
'(0)
(test-org-gen-loc-list "#+BEGIN_SRC emacs-lisp -n \n (- 1 1) \n#+END_SRC"
'src-block)))
;; The first "+n" has 0 lines before it.
(should
;; "-n" resets line number.
(equal '(0)
(test-org-gen-loc-list "#+BEGIN_SRC emacs-lisp -n \n (- 1 1) \n#+END_SRC" 'src-block)))
(test-org-gen-loc-list
"#+BEGIN_SRC emacs-lisp +n \n (+ 0 (- 1 1))\n#+END_SRC"
'src-block)))
;; "-n 10" resets line number but has "9 lines" before it.
(should
;; The first "+n" has 0 lines before it
(equal '(0)
(test-org-gen-loc-list "#+BEGIN_SRC emacs-lisp +n \n (+ 0 (- 1 1))\n#+END_SRC" 'src-block)))
(should
;; "-n 10" resets line number but has "9 lines" before it.
(equal '(9)
(test-org-gen-loc-list "#+BEGIN_SRC emacs-lisp -n 10\n (- 10 1)\n#+END_SRC" 'src-block)))
(test-org-gen-loc-list
"#+BEGIN_SRC emacs-lisp -n 10\n (- 10 1)\n#+END_SRC"
'src-block)))
(should
(equal '(9 25)
(test-org-gen-loc-list "#+BEGIN_SRC emacs-lisp -n 10\n (- 10 1)\n (+ (- 10 1) 1)\n#+END_SRC
#+BEGIN_SRC emacs-lisp +n 15\n (+ (- 10 1) 2 (- 15 1))\n#+END_SRC" 'src-block)))
(test-org-gen-loc-list "
#+BEGIN_SRC emacs-lisp -n 10
(- 10 1)
(+ (- 10 1) 1)
#+END_SRC
#+BEGIN_SRC emacs-lisp +n 15
(+ (- 10 1) 2 (- 15 1))
#+END_SRC"
'src-block)))
(should
(equal '(9 19 0)
(test-org-gen-loc-list "#+BEGIN_SRC emacs-lisp -n 10\n (- 10 1)\n#+END_SRC
#+BEGIN_SRC emacs-lisp +n 10\n (+ (- 10 1) 1 (- 10 1))\n#+END_SRC
#+BEGIN_SRC emacs-lisp -n\n (- 1 1)\n#+END_SRC" 'src-block)))
(test-org-gen-loc-list "
#+BEGIN_SRC emacs-lisp -n 10
(- 10 1)
#+END_SRC
#+BEGIN_SRC emacs-lisp +n 10
(+ (- 10 1) 1 (- 10 1))
#+END_SRC
#+BEGIN_SRC emacs-lisp -n
(- 1 1)
#+END_SRC"
'src-block)))
;; A SRC Block without -n does not add to the line count.
(should
;; an SRC Block without -n does not add to the line count
(equal '(9 "nil" 19)
(equal '(9 no-loc 19)
(test-org-gen-loc-list
"#+BEGIN_SRC emacs-lisp -n 10\n (+ (-10 1) 1)\n#+END_SRC
#+BEGIN_SRC emacs-lisp \n (+ 2 2) \n#+END_SRC
#+BEGIN_SRC emacs-lisp +n 10\n (+ (- 10 1) 1 (- 10 1))\n#+END_SRC" 'src-block))))
"#+BEGIN_SRC emacs-lisp -n 10
(+ (-10 1) 1)
#+END_SRC
#+BEGIN_SRC emacs-lisp
(+ 2 2)
#+END_SRC
#+BEGIN_SRC emacs-lisp +n 10
(+ (- 10 1) 1 (- 10 1))
#+END_SRC"
'src-block))))
(ert-deftest test-org-export/resolve-coderef ()
"Test `org-export-resolve-coderef' specifications."