From my question on the stack overflow, https://stackoverflow.com/questions/51675355/how-to-eval-a-cond-case-and-return-function-object.
(Hy authors reply in a timely manner, but before the question in GitHub issue was rejected haha ha)
My problem is that I need to assemble myself with conditional expressions (cond [P e]).
P is changeable, and E is basically the same. So hopefully with GCC compiled into the intermediate language RTL, do point optimization in the RTL layer, partial evaluation.
To be exact, the e-evaluation is calculated first, and the result of the evaluation of my e-statement is the function object
Then in season 1 load the conditional statement p
In the Season 2 pair (cond [P e]) is evaluated with eval, the desired function object is directly obtained.
The code probably does.
; a fn object (Setv a_fn (fn [x] (+ 1 x))), a mock Predicator (Setv predicator True), inject Predicator and A_FN into a (cond. .) (Setv cond_expr ' (Cond [(~predicator) [~A_FN]]); eval at another place (eval cond_expr)
But this is an error:
Got Typeerror:don ' t know how to wrap <class ' function ';: <function Test_cond_list_fn.<locals>.<lambda > at 0x000001b879fd3d08>
The author's explanation says
Hy's Eval is the first to be compiled into Python's AST. (similar to the GCC front-end language compiled to RTL AST)
But "although you can put abstract objects into hyexpression, but can't compile it"
On the one hand Hy's compiler only accept Hymodel (hyexpression hylist hysymbol There are basic types Hyint hystring and so on),
On the other hand: in the Python ast, function object does not have an explicit representation, so there is no corresponding Hymodel (the same goes for other custom pyobejct)
--but, not completely without solution.
The solution given by the author is not to eval the hyexpression containing the function object but can have the definition of functions
1 compile a function definition.
‘(fn [x] (+ 1 x)))=> (setv cond-expr `(cond [True ~a-fn]))=> (eval cond-expr)<function <lambda> at 0x0000020635231598>
Note that the first line is a normal single quote ', not an anti-quote '
2 Or a function ' s symbol.
=> (defn b-fn [x] (- x 1))=> (setv cond-expr2 `(cond [True b-fn]))=> (eval cond-expr)<function <lambda> at 0x0000020635208378>
Mmmm~ to the AST level, it's a little subtle.
I have to digest it.
Python + lisp Hy's Novice note 2 eval, Hymodel and Python AST