From f81fb771eb458cbe53822ed94f0b6c21a06a5df6 Mon Sep 17 00:00:00 2001 From: gilch Date: Sun, 22 Oct 2017 19:53:05 -0600 Subject: [PATCH] change xi macro to #% tag macro --- NEWS | 1 + docs/extra/anaphoric.rst | 15 ++++++----- hy/extra/anaphoric.hy | 22 ++++++++-------- tests/native_tests/extra/anaphoric.hy | 36 +++++++++++++-------------- 4 files changed, 39 insertions(+), 35 deletions(-) diff --git a/NEWS b/NEWS index cc19a6b..3f0e702 100644 --- a/NEWS +++ b/NEWS @@ -22,6 +22,7 @@ Changes from 0.13.0 * support EDN `#_` syntax to discard the next term * `return` has been implemented as a special form * `while` loops may now contain an `else` clause, like `for` loops + * `xi` from `hy.extra.anaphoric` is now the `#%` tag macro. [ Bug Fixes ] * Numeric literals are no longer parsed as symbols when followed by a dot diff --git a/docs/extra/anaphoric.rst b/docs/extra/anaphoric.rst index 68cb709..56b7cf7 100644 --- a/docs/extra/anaphoric.rst +++ b/docs/extra/anaphoric.rst @@ -229,21 +229,24 @@ Returns a function which applies several forms in series from left to right. The => (op 2) 9 -.. _xi +.. _#% -xi +#% == -Usage ``(xi body ...)`` +Usage ``#%(body ...)`` -Returns a function with parameters implicitly determined by the presence in the body of xi parameters. An xi symbol designates the ith parameter (1-based, e.g. x1, x2, x3, etc.), or all remaining parameters for xi itself. This is not a replacement for fn. The xi forms cannot be nested. +Returns a function with parameters implicitly determined by the presence in +the body of %i parameters. A %i symbol designates the ith parameter +(1-based, e.g. ``%1 %2 %3`` etc.), or all remaining parameters for ``%&``. +Nesting of ``#%()`` forms is not recommended. This is similar to Clojure's anonymous function literals (``#()``). .. code-block:: hy - => ((xi identity [x1 x5 [x2 x3] xi x4]) 1 2 3 4 5 6 7 8) + => (#%(identity [%1 %5 [%2 %3] %& %4]) 1 2 3 4 5 6 7 8) [1, 5, [2, 3,] (6, 7, 8), 4] - => (def add-10 (xi + 10 x1)) + => (def add-10 #%(+ 10 %1)) => (add-10 6) 16 diff --git a/hy/extra/anaphoric.hy b/hy/extra/anaphoric.hy index a99d1cf..f93405a 100644 --- a/hy/extra/anaphoric.hy +++ b/hy/extra/anaphoric.hy @@ -112,25 +112,25 @@ "Returns a function which is the composition of several forms." `(fn [var] (ap-pipe var ~@forms))) -(defmacro xi [&rest body] +(deftag % [body] "Returns a function with parameters implicitly determined by the presence in - the body of xi parameters. An xi symbol designates the ith parameter - (1-based, e.g. x1, x2, x3, etc.), or all remaining parameters for xi itself. - This is not a replacement for fn. The xi forms cannot be nested. " + the body of %i parameters. A %i symbol designates the ith parameter + (1-based, e.g. %1, %2, %3, etc.), or all remaining parameters for %&. + Nesting of #%() forms is not recommended." (setv flatbody (flatten body)) - `(fn [;; generate all xi symbols up to the maximum found in body - ~@(genexpr (HySymbol (+ "x" + `(fn [;; generate all %i symbols up to the maximum found in body + ~@(genexpr (HySymbol (+ "%" (str i))) [i (range 1 - ;; find the maximum xi + ;; find the maximum %i (inc (max (+ (list-comp (int (cut a 1)) [a flatbody] (and (symbol? a) - (.startswith a 'x) + (.startswith a '%) (.isdigit (cut a 1)))) [0]))))]) - ;; generate the &rest parameter only if 'xi is present in body - ~@(if (in 'xi flatbody) - '(&rest xi) + ;; generate the &rest parameter only if '%& is present in body + ~@(if (in '%& flatbody) + '(&rest %&) '())] (~@body))) diff --git a/tests/native_tests/extra/anaphoric.hy b/tests/native_tests/extra/anaphoric.hy index 5a640db..fc45ca5 100644 --- a/tests/native_tests/extra/anaphoric.hy +++ b/tests/native_tests/extra/anaphoric.hy @@ -99,28 +99,28 @@ (assert-equal ((ap-compose (+ it 1) (* it 3)) 2) 9) (assert-equal ((ap-compose (list (rest it)) (len it)) [4 5 6 7]) 3)) -(defn test-xi [] - "NATIVE: testing xi forms" +(defn test-tag-fn [] + "NATIVE: testing #%() forms" ;; test ordering - (assert-equal ((xi / x1 x2) 2 4) 0.5) - (assert-equal ((xi / x2 x1) 2 4) 2) - (assert-equal ((xi identity (, x5 x4 x3 x2 x1)) 1 2 3 4 5) (, 5 4 3 2 1)) - (assert-equal ((xi identity (, x1 x2 x3 x4 x5)) 1 2 3 4 5) (, 1 2 3 4 5)) - (assert-equal ((xi identity (, x1 x5 x2 x3 x4)) 1 2 3 4 5) (, 1 5 2 3 4)) + (assert-equal (#%(/ %1 %2) 2 4) 0.5) + (assert-equal (#%(/ %2 %1) 2 4) 2) + (assert-equal (#%(identity (, %5 %4 %3 %2 %1)) 1 2 3 4 5) (, 5 4 3 2 1)) + (assert-equal (#%(identity (, %1 %2 %3 %4 %5)) 1 2 3 4 5) (, 1 2 3 4 5)) + (assert-equal (#%(identity (, %1 %5 %2 %3 %4)) 1 2 3 4 5) (, 1 5 2 3 4)) ;; test &rest - (assert-equal ((xi sum xi) 1 2 3) 6) - (assert-equal ((xi identity (, x1 xi)) 10 1 2 3) (, 10 (, 1 2 3))) + (assert-equal (#%(sum %&) 1 2 3) 6) + (assert-equal (#%(identity (, %1 %&)) 10 1 2 3) (, 10 (, 1 2 3))) ;; no parameters - (assert-equal ((xi list)) []) - (assert-equal ((xi identity "Hy!")) "Hy!") - (assert-equal ((xi identity "xi")) "xi") - (assert-equal ((xi + "Hy " "world!")) "Hy world!") + (assert-equal (#%(list)) []) + (assert-equal (#%(identity "Hy!")) "Hy!") + (assert-equal (#%(identity "%&")) "%&") + (assert-equal (#%(+ "Hy " "world!")) "Hy world!") ;; test skipped parameters - (assert-equal ((xi identity [x3 x1]) 1 2 3) [3 1]) + (assert-equal (#%(identity [%3 %1]) 1 2 3) [3 1]) ;; test nesting - (assert-equal ((xi identity [x1 (, x2 [x3] "Hy" [xi])]) 1 2 3 4 5) + (assert-equal (#%(identity [%1 (, %2 [%3] "Hy" [%&])]) 1 2 3 4 5) [1 (, 2 [3] "Hy" [(, 4 5)])]) ;; test arg as function - (assert-equal ((xi x1 2 4) +) 6) - (assert-equal ((xi x1 2 4) -) -2) - (assert-equal ((xi x1 2 4) /) 0.5)) + (assert-equal (#%(%1 2 4) +) 6) + (assert-equal (#%(%1 2 4) -) -2) + (assert-equal (#%(%1 2 4) /) 0.5))