%* %** parameters for #% tag macro
This commit is contained in:
parent
f81fb771eb
commit
b5f1136ba5
3
NEWS
3
NEWS
@ -22,7 +22,8 @@ Changes from 0.13.0
|
|||||||
* support EDN `#_` syntax to discard the next term
|
* support EDN `#_` syntax to discard the next term
|
||||||
* `return` has been implemented as a special form
|
* `return` has been implemented as a special form
|
||||||
* `while` loops may now contain an `else` clause, like `for` loops
|
* `while` loops may now contain an `else` clause, like `for` loops
|
||||||
* `xi` from `hy.extra.anaphoric` is now the `#%` tag macro.
|
* `xi` from `hy.extra.anaphoric` is now the `#%` tag macro
|
||||||
|
* `#%` also has a new `&kwargs` parameter `%**`.
|
||||||
|
|
||||||
[ Bug Fixes ]
|
[ Bug Fixes ]
|
||||||
* Numeric literals are no longer parsed as symbols when followed by a dot
|
* Numeric literals are no longer parsed as symbols when followed by a dot
|
||||||
|
@ -236,16 +236,17 @@ Returns a function which applies several forms in series from left to right. The
|
|||||||
|
|
||||||
Usage ``#%(body ...)``
|
Usage ``#%(body ...)``
|
||||||
|
|
||||||
Returns a function with parameters implicitly determined by the presence in
|
Makes a function with an implicit parameter list from ``%`` parameters.
|
||||||
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 ``%&``.
|
A ``%i`` symbol designates the `i` th parameter (1-based, e.g. ``%1 %2 %3`` etc.).
|
||||||
|
``%*`` and ``%**`` name the ``&rest`` and ``&kwargs`` parameters, respectively.
|
||||||
Nesting of ``#%()`` forms is not recommended.
|
Nesting of ``#%()`` forms is not recommended.
|
||||||
|
|
||||||
This is similar to Clojure's anonymous function literals (``#()``).
|
This is similar to Clojure's anonymous function literals (``#()``).
|
||||||
|
|
||||||
.. code-block:: hy
|
.. code-block:: hy
|
||||||
|
|
||||||
=> (#%(identity [%1 %5 [%2 %3] %& %4]) 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]
|
[1, 5, [2, 3,] (6, 7, 8), 4]
|
||||||
=> (def add-10 #%(+ 10 %1))
|
=> (def add-10 #%(+ 10 %1))
|
||||||
=> (add-10 6)
|
=> (add-10 6)
|
||||||
|
@ -113,24 +113,28 @@
|
|||||||
`(fn [var] (ap-pipe var ~@forms)))
|
`(fn [var] (ap-pipe var ~@forms)))
|
||||||
|
|
||||||
(deftag % [body]
|
(deftag % [body]
|
||||||
"Returns a function with parameters implicitly determined by the presence in
|
"makes a function with an implicit parameter list from `%` parameters.
|
||||||
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 %&.
|
A %i symbol designates the ith parameter (1-based, e.g. `%1 %2 %3` etc.).
|
||||||
Nesting of #%() forms is not recommended."
|
`%*` and `%**` name the `&rest` and `&kwargs` parameters, respectively.
|
||||||
|
Nesting of `#%()` forms is not recommended."
|
||||||
(setv flatbody (flatten body))
|
(setv flatbody (flatten body))
|
||||||
`(fn [;; generate all %i symbols up to the maximum found in body
|
`(fn [;; generate all %i symbols up to the maximum found in body
|
||||||
~@(genexpr (HySymbol (+ "%"
|
~@(genexpr (HySymbol (+ "%"
|
||||||
(str i)))
|
(str i)))
|
||||||
[i (range 1
|
[i (range 1
|
||||||
;; find the maximum %i
|
;; find the maximum %i
|
||||||
(inc (max (+ (list-comp (int (cut a 1))
|
(-> (list-comp (int (cut a 1))
|
||||||
[a flatbody]
|
[a flatbody]
|
||||||
(and (symbol? a)
|
(and (symbol? a)
|
||||||
(.startswith a '%)
|
(.startswith a '%)
|
||||||
(.isdigit (cut a 1))))
|
(.isdigit (cut a 1))))
|
||||||
[0]))))])
|
(+ [0])
|
||||||
;; generate the &rest parameter only if '%& is present in body
|
max
|
||||||
~@(if (in '%& flatbody)
|
inc))])
|
||||||
'(&rest %&)
|
;; generate the &rest parameter only if '%* is present in body
|
||||||
'())]
|
~@(if (in '%* flatbody)
|
||||||
|
'(&rest %*))
|
||||||
|
~@(if (in '%** flatbody)
|
||||||
|
'(&kwargs %**))]
|
||||||
(~@body)))
|
(~@body)))
|
||||||
|
@ -108,19 +108,23 @@
|
|||||||
(assert-equal (#%(identity (, %1 %2 %3 %4 %5)) 1 2 3 4 5) (, 1 2 3 4 5))
|
(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))
|
(assert-equal (#%(identity (, %1 %5 %2 %3 %4)) 1 2 3 4 5) (, 1 5 2 3 4))
|
||||||
;; test &rest
|
;; test &rest
|
||||||
(assert-equal (#%(sum %&) 1 2 3) 6)
|
(assert-equal (#%(sum %*) 1 2 3) 6)
|
||||||
(assert-equal (#%(identity (, %1 %&)) 10 1 2 3) (, 10 (, 1 2 3)))
|
(assert-equal (#%(identity (, %1 %*)) 10 1 2 3) (, 10 (, 1 2 3)))
|
||||||
;; no parameters
|
;; no parameters
|
||||||
(assert-equal (#%(list)) [])
|
(assert-equal (#%(list)) [])
|
||||||
(assert-equal (#%(identity "Hy!")) "Hy!")
|
(assert-equal (#%(identity "Hy!")) "Hy!")
|
||||||
(assert-equal (#%(identity "%&")) "%&")
|
(assert-equal (#%(identity "%*")) "%*")
|
||||||
(assert-equal (#%(+ "Hy " "world!")) "Hy world!")
|
(assert-equal (#%(+ "Hy " "world!")) "Hy world!")
|
||||||
;; test skipped parameters
|
;; test skipped parameters
|
||||||
(assert-equal (#%(identity [%3 %1]) 1 2 3) [3 1])
|
(assert-equal (#%(identity [%3 %1]) 1 2 3) [3 1])
|
||||||
;; test nesting
|
;; test nesting
|
||||||
(assert-equal (#%(identity [%1 (, %2 [%3] "Hy" [%&])]) 1 2 3 4 5)
|
(assert-equal (#%(identity [%1 (, %2 [%3] "Hy" [%*])]) 1 2 3 4 5)
|
||||||
[1 (, 2 [3] "Hy" [(, 4 5)])])
|
[1 (, 2 [3] "Hy" [(, 4 5)])])
|
||||||
;; test arg as function
|
;; test arg as function
|
||||||
(assert-equal (#%(%1 2 4) +) 6)
|
(assert-equal (#%(%1 2 4) +) 6)
|
||||||
(assert-equal (#%(%1 2 4) -) -2)
|
(assert-equal (#%(%1 2 4) -) -2)
|
||||||
(assert-equal (#%(%1 2 4) /) 0.5))
|
(assert-equal (#%(%1 2 4) /) 0.5)
|
||||||
|
;; test &rest &kwargs
|
||||||
|
(assert-equal (#%(, %* %**) 1 2 :a 'b)
|
||||||
|
(, (, 1 2)
|
||||||
|
(dict :a 'b))))
|
||||||
|
Loading…
x
Reference in New Issue
Block a user