On 2016-11-06 21:46, Steven D'Aprano wrote:
I sometimes think that such unevaluated expressions (which I usually
call "thunks") would be cool to have. But in more realistic moments I
think that they're a solution looking for a problem to solve.

If your PEP suggests a problem that they will solve, I'm interested.

But note that we already have two ways of generating thunk-like objects:
functions and compiled byte-code.

thunk = lambda: a + b - c
thunk()

thunk = compile('a + b - c', '', 'single')
eval(thunk)

Both are very heavyweight: the overhead of function call syntax is
significant, and the keyword "lambda" is a lot of typing just to delay
evaluation of an expression. compile(...) is even worse.

I sometimes want these too. But note that both the solutions you propose are quite a ways from a true "unevaluated expression".

The big problem with an ordinary lambda (or def) is that you cannot explicitly control where it will decide to look for its free variables. If it uses a local variable from an enclosing namespace, it will always look for it in that namespace, so you can't "patch in" a value by setting a global variable. If it uses a variable that isn't local to any enclosing namespace, it will always look for it in the global namespace, so you can't patch in a value by setting a local variable in the context where you're calling the function.

You can get around this in a def by, for instance, using global to mark all variables global, and then using eval to pass in a custom global namespace. But that is a lot of boilerplate. What I want (when I want this) is a way to create a function that will allow the injection of values for *any* variables, regardless of whether the function originally thought they were local, nonlocal (i.e., local to some enclosing scope) or global. The way it is now, the status of a function's variables is inextricably linked to the syntactic context where it was defined. This is a good thing most of the time, but it's not what you want if you want to define an expression that should later be evaluated in some other context.

I consider the compile-based solution a nonstarter, because it puts the code in a string. With the code in a string, you are blocked from using syntax highlighting or any other handy editor features.

--
Brendan Barnwell
"Do not follow where the path may lead. Go, instead, where there is no path, and leave a trail."
   --author unknown
_______________________________________________
Python-ideas mailing list
[email protected]
https://mail.python.org/mailman/listinfo/python-ideas
Code of Conduct: http://python.org/psf/codeofconduct/

Reply via email to