[Python-Dev] __future__ and eval()
Hi guys, when developing my dedent tool, I stumbled over the following behavior: In dedent, I had the line from __future__ import print_function Later in the script, I do some exec(the_script) and I was surprised: The exec() script inherited the __future__ statement! It behaved like the future statement were implicitly there. Is that a bug or a feature? You can try the effect by "pip install dedent" and adding the future statement there. I'd like to know if this is a bug (and I think so) -- Christian Tismer :^) [email protected] Software Consulting : http://www.stackless.com/ Karl-Liebknecht-Str. 121 : https://github.com/PySide 14482 Potsdam: GPG key -> 0xFB7BEE0E phone +49 173 24 18 776 fax +49 (30) 700143-0023 ___ Python-Dev mailing list [email protected] https://mail.python.org/mailman/listinfo/python-dev Unsubscribe: https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] __future__ and eval()
On Sat, Oct 1, 2016 at 9:39 PM, Christian Tismer wrote:
> The exec() script inherited the __future__ statement!
> It behaved like the future statement were implicitly there.
>
> Is that a bug or a feature?
It's documented, but not very noisily.
https://docs.python.org/2/reference/simple_stmts.html#future-statements
So if you want to isolate the execution environments, you can use
compile() explicitly. Without isolation:
Python 2.7.12+ (default, Sep 1 2016, 20:27:38)
[GCC 6.2.0 20160822] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> exec(compile("print('hello','world')", "-", "exec"))
('hello', 'world')
>>> exec(compile("from __future__ import print_function;
>>> print('hello','world')", "-", "exec"))
hello world
>>> from __future__ import print_function
>>> exec(compile("print('hello','world')", "-", "exec"))
hello world
>>> exec(compile("from __future__ import print_function;
>>> print('hello','world')", "-", "exec"))
hello world
With isolation:
>>> exec(compile("print('hello','world')", "-", "exec", 0, 1))
('hello', 'world')
>>> exec(compile("from __future__ import print_function;
>>> print('hello','world')", "-", "exec", 0, 1))
hello world
So I'd call it a feature, but possibly one that warrants a mention in
the exec and eval docs. Maybe something like:
https://docs.python.org/2/reference/simple_stmts.html#the-exec-statement
[2] When strings are executed, __future__ directives active in the
surrounding context will be active for the compiled code also. If this
is not desired, see the compile() function's dont_inherit parameter.
Would that clarify?
ChrisA
___
Python-Dev mailing list
[email protected]
https://mail.python.org/mailman/listinfo/python-dev
Unsubscribe:
https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] __future__ and eval()
On Sat, Oct 1, 2016 at 10:17 PM, Chris Angelico wrote: > So I'd call it a feature, but possibly one that warrants a mention in > the exec and eval docs. To clarify: This *is* documented under __future__, but not under exec/eval. I'm just suggesting adding another cross-reference. ChrisA ___ Python-Dev mailing list [email protected] https://mail.python.org/mailman/listinfo/python-dev Unsubscribe: https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
Re: [Python-Dev] __future__ and eval()
Ah, interesting!
Thanks for the clarification. So it is really possible to write
code with an implicit future statement in it, or to switch the behavior
off.
Good to know. I will probably not use it, since I can't decide on a good
default, but getting rid of print_statement is tempting...
> https://docs.python.org/2/reference/simple_stmts.html#the-exec-statement
>
> [2] When strings are executed, __future__ directives active in the
> surrounding context will be active for the compiled code also. If this
> is not desired, see the compile() function's dont_inherit parameter.
>
> Would that clarify?
Yes please, that would be a good place to document it. For some reason
I did not look up __future__.
Thanks -- Chris
On 01/10/16 14:17, Chris Angelico wrote:
On Sat, Oct 1, 2016 at 9:39 PM, Christian Tismer wrote:
The exec() script inherited the __future__ statement!
It behaved like the future statement were implicitly there.
Is that a bug or a feature?
It's documented, but not very noisily.
https://docs.python.org/2/reference/simple_stmts.html#future-statements
So if you want to isolate the execution environments, you can use
compile() explicitly. Without isolation:
Python 2.7.12+ (default, Sep 1 2016, 20:27:38)
[GCC 6.2.0 20160822] on linux2
Type "help", "copyright", "credits" or "license" for more information.
exec(compile("print('hello','world')", "-", "exec"))
('hello', 'world')
exec(compile("from __future__ import print_function; print('hello','world')", "-",
"exec"))
hello world
from __future__ import print_function
exec(compile("print('hello','world')", "-", "exec"))
hello world
exec(compile("from __future__ import print_function; print('hello','world')", "-",
"exec"))
hello world
With isolation:
exec(compile("print('hello','world')", "-", "exec", 0, 1))
('hello', 'world')
exec(compile("from __future__ import print_function; print('hello','world')", "-",
"exec", 0, 1))
hello world
So I'd call it a feature, but possibly one that warrants a mention in
the exec and eval docs. Maybe something like:
https://docs.python.org/2/reference/simple_stmts.html#the-exec-statement
[2] When strings are executed, __future__ directives active in the
surrounding context will be active for the compiled code also. If this
is not desired, see the compile() function's dont_inherit parameter.
Would that clarify?
ChrisA
___
Python-Dev mailing list
[email protected]
https://mail.python.org/mailman/listinfo/python-dev
Unsubscribe:
https://mail.python.org/mailman/options/python-dev/tismer%40stackless.com
--
Christian Tismer :^) [email protected]
Software Consulting : http://www.stackless.com/
Karl-Liebknecht-Str. 121 : https://github.com/PySide
14482 Potsdam: GPG key -> 0xFB7BEE0E
phone +49 173 24 18 776 fax +49 (30) 700143-0023
___
Python-Dev mailing list
[email protected]
https://mail.python.org/mailman/listinfo/python-dev
Unsubscribe:
https://mail.python.org/mailman/options/python-dev/archive%40mail-archive.com
