[英]Why doesn't exec(“break”) work inside a while loop
As the question asks, why doesn't the below code work: 正如问题所问,为什么以下代码不起作用:
while True:
exec("break")
I am executing the above in pycharm via python 3.5.2 console. 我通过python 3.5.2控制台在pycharm中执行上面的操作。 I initially thought it was a context issue but after reading the documentation, I haven't come closer to understanding why this error ocurs.
我最初认为这是一个上下文问题,但在阅读文档之后,我还没有接近理解为什么会发生这种错误。
SyntaxError: 'break' outside loop
Thanks in advance :) 提前致谢 :)
EDIT: I understand that it works without exec() by the way, I'm curious why it won't work with exec (as my circumstances required it) - comprehensive answers welcome. 编辑:我知道它的工作没有exec()顺便说一句,我很好奇为什么它不能与exec一起工作(因为我的情况需要它) - 全面的答案欢迎。
This is because exec()
is ignorant to your surrounding while loop. 这是因为
exec()
对你周围的循环无知。 So the only statement that exec()
sees in your example is break
. 因此,
exec()
在您的示例中看到的唯一语句是break
。 Instead of using exec("break")
, simply use break
as is. 而不是使用
exec("break")
,只需使用break
。
The only access the exec()
function has to its surrounding scope, is the globals()
and locals()
dictionaries. exec()
函数对其周围范围的唯一访问是globals()
和locals()
字典。 The documentation for exec()
provides some insight into how exec()
works: exec()
的文档提供了一些有关exec()
如何工作的见解:
This function supports dynamic execution of Python code.
此函数支持Python代码的动态执行。 object must be either a string or a code object.
object必须是字符串或代码对象。 If it is a string, the string is parsed as a suite of Python statements which is then executed (unless a syntax error occurs).
如果它是一个字符串,则将该字符串解析为一组Python语句,然后执行该语句(除非发生语法错误)。 [1] If it is a code object, it is simply executed.
[1]如果是代码对象,则只执行它。 In all cases, the code that's executed is expected to be valid as file input (see the section “File input” in the Reference Manual).
在所有情况下,执行的代码应该作为文件输入有效(请参见“参考手册”中的“文件输入”部分)。 Be aware that the return and yield statements may not be used outside of function definitions even within the context of code passed to the exec() function.
请注意,即使在传递给exec()函数的代码的上下文中,也不能在函数定义之外使用return和yield语句。 The return value is None.
返回值为None。
In all cases, if the optional parts are omitted, the code is executed in the current scope.
在所有情况下,如果省略可选部分,则代码在当前范围内执行。 If only globals is provided, it must be a dictionary, which will be used for both the global and the local variables.
如果只提供全局变量,则它必须是字典,它将用于全局变量和局部变量。 If globals and locals are given, they are used for the global and local variables, respectively.
如果给出全局变量和局部变量,则它们分别用于全局变量和局部变量。 If provided, locals can be any mapping object.
如果提供,则locals可以是任何映射对象。 Remember that at module level, globals and locals are the same dictionary.
请记住,在模块级别,全局变量和本地变量是相同的字典。 If exec gets two separate objects as globals and locals, the code will be executed as if it were embedded in a class definition.
如果exec获得两个单独的对象作为全局变量和局部变量,则代码将被执行,就像它嵌入在类定义中一样。
If the globals dictionary does not contain a value for the key builtins , a reference to the dictionary of the built-in module builtins is inserted under that key.
如果全局字典不包含键内置函数的值,则在该键下插入对内置模块内置字典的引用。 That way you can control what builtins are available to the executed code by inserting your own builtins dictionary into globals before passing it to exec().
这样,通过将自己的内置字典插入到globals中,然后将其传递给exec(),就可以控制执行代码可用的内置函数。
The exec
statement runs a bit of code independently from the rest of your code. exec
语句独立于代码的其余部分运行一些代码。
Hence, the line: 因此,该行:
exec("break")
is tantamount to calling break
out of nowhere, in a script where nothing else happens, and where no loop exists. 等于在一个没有其他任何事情的脚本中调用
break
冒出的地方,并且没有循环存在。
The right way to call the break
statement is: 调用
break
语句的正确方法是:
while True:
break
EDIT 编辑
The comment from Leaf made me think about it. Leaf的评论让我思考它。
Actually, the exec
statement does not run the code out of nowhere. 实际上,
exec
语句不会无处运行代码。
>>> i = 12
>>> exec("print(i)")
12
A better answer, as far as I understand, is that exec
runs a piece of code in the same environment as the original code, but independently from it. 据我所知,一个更好的答案是
exec
在与原始代码相同的环境中运行一段代码,但独立于它。
This basically means that all the variables that exist at the moment exec
is called can be used in the code called by exec
. 这基本上意味着,所有存在此刻的变量
exec
被称为可以通过调用的代码中使用exec
。 But the context is all new, so return
, break
, continue
and other statements that need a context, will not work, unless the right context is created. 但是上下文都是新的,所以
return
, break
, continue
和其他需要上下文的语句都不会起作用,除非创建了正确的上下文。
By the way, I kept the word "statement" when talking about exec
, but it has become a function in Python3, the same way print
did. 顺便说一下,在谈论
exec
时我保留了“声明”这个词,但它已经成为Python3中的一个函数,就像print
一样。
exec()
is a function. exec()
是一个函数。 Assuming for simplicity that a function call constitutes a statement of its own (just like in your example), it may end in one of the following ways: 假设为简单起见,函数调用构成了自己的语句(就像在您的示例中一样),它可能以下列方式之一结束:
the function returns normally - in this case the next statement according to the control flow is executed; 函数正常返回 - 在这种情况下,执行根据控制流的下一个语句;
an exception is raised/thrown from the function - in this case the matching except
clause on the call stack (if any) is executed 从函数引发/抛出异常 - 在这种情况下,执行调用堆栈上的匹配
except
子句(如果有)
the entire program is terminated due to an explicit call to exit() or equivalent - there is nothing to execute. 由于显式调用exit()或等效函数,整个程序终止 - 没有任何东西可以执行。
Calling a break
(as well as return
or yield
) from inside exec()
would modify the program execution flow in a way that is incompatible with the described aspect of the function call semantics. 从
exec()
内部调用break
(以及return
或yield
)将以与函数调用语义的描述方面不兼容的方式修改程序执行流。
Note that the documentation on exec()
contains a special note on the use of return
and yield
inside exec()
: 请注意, 在文件
exec()
包含对使用的特殊说明, return
和yield
内部exec()
Be aware that the
return
andyield
statements may not be used outside of function definitions even within the context of code passed to theexec()
function.请注意,即使在传递给
exec()
函数的代码的上下文中,也不能在函数定义之外使用return
和yield
语句。
A similar restriction applies to the break
statement (with the difference that it may not be used outside loops ), and I wonder why it was not included in the documentation. 类似的限制适用于
break
语句(区别在于它可能不在循环外使用),我想知道为什么它没有包含在文档中。
exec
is a built in function , exec
是内置函数,
Python insists that break
should happen inside the loop,not inside a function
Python坚持认为
break
应该在循环内部发生,而不是在function
内部发生
What is happening in your code is you are putting break
inside a function
which is exec
you can't break out of a loop by executing a break
within a function that's called inside the loop. 什么在你的代码的情况是你把
break
一个内部function
是exec
你无法通过执行跳出循环的break
一这就是所谓的内循环功能内。
For Ex 对于Ex
>>> def func():
break
SyntaxError: 'break' outside loop
>>>
Try break without exec(): 尝试在没有exec()的情况下休息:
while True:
break
exec
function runs code inside a code and that means it runs out of nowhere! exec
函数在代码中运行代码,这意味着它无处不在! So, your while loop doesn't catch it. 所以,你的while循环没有抓住它。 Your file is
<stdin>
. 您的文件是
<stdin>
。 exec
runs on another file called <string>
. exec
在另一个名为<string>
文件上运行。 it doesn't recognize it where are you trying to break a loop where there is not a loop. 它无法识别它在哪里试图打破没有循环的循环。 So, your code is this:
所以,你的代码是这样的:
while True:
exec("break")
It should be like this: 它应该是这样的:
while True:
break
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.