branch: elpa/loopy
commit bfbb50124b4d0b973a591b101d4326c764804530
Author: okamsn <[email protected]>
Commit: GitHub <[email protected]>

    Make incompatible accumulation initializations an error. (#254)
    
    - `loopy--process-instruction`: signal the error.
    - Add new tests:
      - `accumulation-compatibility-different-inits-1`
      - `accumulation-compatibility-different-inits-2`
    - Update Org documentation to note that an error is signaled.
    - Update README and CHANGELOG.
    
    Closes issue #169.
---
 CHANGELOG.md      |  7 +++++++
 README.org        |  3 +++
 doc/loopy-doc.org |  5 +++--
 doc/loopy.texi    | 15 ++++++++-------
 lisp/loopy.el     | 12 +++---------
 tests/tests.el    | 54 ++++++++++++++++++++++++++----------------------------
 6 files changed, 50 insertions(+), 46 deletions(-)

diff --git a/CHANGELOG.md b/CHANGELOG.md
index 67e98beea96..aca641bbe36 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -13,6 +13,13 @@ For Loopy Dash, see <https://github.com/okamsn/loopy-dash>.
   More specifically, keep the same order returned by `pcase` for the binding of
   those final variables.
 
+### Breaking Changes
+
+- Using accumulation commands with different initial values for the same
+  variable now signals an error instead of a warning ([#169], [#254]).
+
+[#169]: https://github.com/okamsn/loopy/issues/169
+[#254]: https://github.com/okamsn/loopy/PR/254
 [#251]: https://github.com/okamsn/loopy/PR/251
 
 ## 0.15.0
diff --git a/README.org b/README.org
index 3a56314d9a4..03cea94b177 100644
--- a/README.org
+++ b/README.org
@@ -35,6 +35,9 @@ please let me know.
 -----
 
  _Recent breaking changes:_
+ - Unreleased:
+   - Using accumulation commands with different initial values for the same
+     variable now signals an error instead of a warning.
  - Version 0.15.0:
    - Loopy now requires at least Emacs version 28.1, increased from version
      27.1.
diff --git a/doc/loopy-doc.org b/doc/loopy-doc.org
index b01e1a2d6a1..c386645824b 100644
--- a/doc/loopy-doc.org
+++ b/doc/loopy-doc.org
@@ -2997,6 +2997,8 @@ documentation tries to note when it is not ~nil~.  For 
example, the default
 starting value for the =sum= command is ~0~ and the default starting value for
 the =multiply= command is ~1~.  The default initialization value used by an
 accumulation command can be overridden using the =with= special macro argument.
+If two commands use different initial values and the =with= special
+macro argument is not used, an error is signaled.
 
 #+attr_texinfo: :tag Warning
 #+begin_quote
@@ -3006,9 +3008,8 @@ conflict, use the =with= special macro argument, as noted 
above.
 #+end_quote
 
 #+begin_src emacs-lisp
-  ;; Raises a warning. Will raise an error in the future.
+  ;; Signals an error:
   ;;
-  ;; => 27
   (loopy (numbers i :from 1 :to 3)
          (sum my-accum i) ; Defaults to 0.
          (multiply my-accum i) ; Defaults to 1.
diff --git a/doc/loopy.texi b/doc/loopy.texi
index 4ed390af518..825c41d7a99 100644
--- a/doc/loopy.texi
+++ b/doc/loopy.texi
@@ -746,7 +746,7 @@ You should keep in mind that commands are evaluated in 
order.  This means that
 attempting something like the below example might not do what you expect, as 
@samp{i}
 is assigned a value from the list after collecting @samp{i} into @samp{coll}.
 
-@float Listing,org572b5bd
+@float Listing,orga23c8aa
 @lisp
 ;; => (nil 1 2)
 (loopy (collect coll i)
@@ -935,7 +935,7 @@ the flag @samp{dash} provided by the package 
@samp{loopy-dash}.
 
 Below are two examples of destructuring in @code{cl-loop} and @code{loopy}.
 
-@float Listing,org99c53b0
+@float Listing,orgea50e00
 @lisp
 ;; => (1 2 3 4)
 (cl-loop for (i . j) in '((1 . 2) (3 . 4))
@@ -950,7 +950,7 @@ Below are two examples of destructuring in @code{cl-loop} 
and @code{loopy}.
 @caption{Destructuring values in a list.}
 @end float
 
-@float Listing,org7212adc
+@float Listing,org5e2a634
 @lisp
 ;; => (1 2 3 4)
 (cl-loop for elem in '((1 . 2) (3 . 4))
@@ -3206,6 +3206,8 @@ documentation tries to note when it is not @code{nil}.  
For example, the default
 starting value for the @samp{sum} command is @code{0} and the default starting 
value for
 the @samp{multiply} command is @code{1}.  The default initialization value 
used by an
 accumulation command can be overridden using the @samp{with} special macro 
argument.
+If two commands use different initial values and the @samp{with} special
+macro argument is not used, an error is signaled.
 
 @quotation Warning
 Currently, a warning is raised when the default initial values of accumulation
@@ -3215,9 +3217,8 @@ conflict, use the @samp{with} special macro argument, as 
noted above.
 @end quotation
 
 @lisp
-;; Raises a warning. Will raise an error in the future.
+;; Signals an error:
 ;;
-;; => 27
 (loopy (numbers i :from 1 :to 3)
        (sum my-accum i) ; Defaults to 0.
        (multiply my-accum i) ; Defaults to 1.
@@ -4970,7 +4971,7 @@ using the @code{let*} special form.
 This method recognizes all commands and their aliases in the user option
 @code{loopy-parsers}.
 
-@float Listing,org0175e90
+@float Listing,orge907358
 @lisp
 ;; => ((-9 -8 -7 -6 -5 -4 -3 -2 -1)
 ;;     (0)
@@ -5552,7 +5553,7 @@ between aliases and preferred names (which are the ones 
commonly used and listed
 first in this document).  We continue to use the word ``alias'' for its common
 definition rather than to suggest a difference in the code.
 
-@float Listing,org7c76d17
+@float Listing,org3b20adc
 @lisp
 ;; => ("a" "b" "c" "d")
 (loopy (array i "abcd")
diff --git a/lisp/loopy.el b/lisp/loopy.el
index b526e057d82..b0f0017cc7c 100644
--- a/lisp/loopy.el
+++ b/lisp/loopy.el
@@ -661,16 +661,10 @@ macro `loopy' itself."
        (pcase-let ((`(,var ,new-val) instruction-value))
          (pcase var
            ((pred loopy--with-bound-p) nil)
-           ((and (app loopy--command-bound-p `(,_place . ,old-val))
+           ((and (app loopy--command-bound-p `(,place . ,old-val))
                  (guard (not (equal new-val old-val))))
-            ;; TODO: Switch from raising a warning to raising an error.
-            ;; (signal 'loopy-incompatible-accumulation-initializations
-            ;;         (list :in place :var var :old old-val :new new-val))
-            (display-warning
-             'loopy
-             (format "loopy: Conflicting accumulation starting values: `%s', 
%s, %s\nThis will be an error in the future.  To resolve this error, use `with' 
to explicitly specify a starting value."
-                     var old-val new-val)
-             :warning))
+            (signal 'loopy-incompatible-accumulation-initializations
+                    (list :in place :var var :old old-val :new new-val)))
            (_ (push instruction-value loopy--accumulation-vars)))))
 
       (loopy--other-vars
diff --git a/tests/tests.el b/tests/tests.el
index a85ffbc5c81..3d6c5c981ce 100644
--- a/tests/tests.el
+++ b/tests/tests.el
@@ -4128,34 +4128,32 @@ expansion time."
               (nunion . nunioning)
               (nconc . nconcing)))
 
-;; TODO: Enable these tests in a future version.
-;;
-;; (loopy-deftest accumulation-compatibility-different-inits-1
-;;   :doc "Check that accumulation commands with different initial values 
raise an error.
-;; This should apply even when they're compatible types."
-;;   :error loopy-incompatible-accumulation-initializations
-;;   :macroexpand t
-;;   :body ((list i '(1 2 3 4 5))
-;;          (sum i)
-;;          (multiply i))
-;;   :loopy t
-;;   :iter-keyword (list sum multiply)
-;;   :iter-bare ((list . listing)
-;;               (sum . summing)
-;;               (multiply . multiplying)))
-;;
-;; (loopy-deftest accumulation-compatibility-different-inits-2
-;;   :doc "Check that `with' on the variable (see test 1) avoids the error."
-;;   :result 27
-;;   :body ((with (loopy-result 0))
-;;          (list i '(1 2 3))
-;;          (sum i)
-;;          (multiply i))
-;;   :loopy t
-;;   :iter-keyword (list sum multiply)
-;;   :iter-bare ((list . listing)
-;;               (sum . summing)
-;;               (multiply . multiplying)))
+(loopy-deftest accumulation-compatibility-different-inits-1
+  :doc "Check that accumulation commands with different initial values raise 
an error.
+This should apply even when they're compatible types."
+  :error loopy-incompatible-accumulation-initializations
+  :macroexpand t
+  :body ((list i '(1 2 3 4 5))
+         (sum i)
+         (multiply i))
+  :loopy t
+  :iter-keyword (list sum multiply)
+  :iter-bare ((list . listing)
+              (sum . summing)
+              (multiply . multiplying)))
+
+(loopy-deftest accumulation-compatibility-different-inits-2
+  :doc "Check that `with' on the variable (see test 1) avoids the error."
+  :result 27
+  :body ((with (loopy-result 0))
+         (list i '(1 2 3))
+         (sum i)
+         (multiply i))
+  :loopy t
+  :iter-keyword (list sum multiply)
+  :iter-bare ((list . listing)
+              (sum . summing)
+              (multiply . multiplying)))
 
 (loopy-deftest accumulation-compatibility-different-types
   :doc "Check that commands with different accumulation types should raise 
error."

Reply via email to