范围,类型和UnboundLocalError [英] Scope, type and UnboundLocalError

查看:47
本文介绍了范围,类型和UnboundLocalError的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述



我试图找出为什么在从int处于全局范围的函数访问

int时得到UnboundLocalError,而不是

明确地声明它是全局的,但在访问

类似情况下的列表时却没有。


文档: http://docs.python.org/ref/naming.html 没有给出

我足够的信息来确定为什么差异存在,因为它没有

似乎提到类型..


代码:


===== scope_and_type.py =======

m = 0

n = [0]


def int_access0():

m = m + 1

返回m

def int_access1() :

m + = 1

返回m

def list_access0():

n [0] = n [0 ] + 1

返回n

def list_access1():

n [0] + = 1

返回n


尝试:

print" \ nint_access0:",int_access0()

除了UnboundLocalError,inst:

print"错误:\ n",inst

尝试:

print" \ nint_access1:",int_access1()
除了UnboundLocalError之外的
, inst:

print"错误:\ n",inst

试试:

print" \ nlist_access0:",list_access0()
除了UnboundLocalError之外的
, inst:

print"错误:\ n",inst

试试:

print" \ nlist_access1:",list_access1()
除了UnboundLocalError之外的
, inst:

print"错误:\ n",inst

print" \\\
(m,n)=",(m,n)

p =(0,)

def tuple_access():

返回p [0]

尝试:

print" \\\ teuple_acces: ",tuple_access()

除了UnboundLocalError,inst:

print"错误:\ n",inst

print" \ np =",p


===== END scope_and_type.py == =====


输出:


>>>



int_access0:错误:

分配前引用的局部变量''m'


int_access1:错误:

分配前引用的局部变量m


list_access0:[1]


list_access1:[2]


(m,n)=(0,[2])


tuple_acces:0

p =(0,)


>>>

解决方案



Paddy写道:




我想弄清楚为什么在从int所在的函数访问

int时会得到UnboundLocalError全局范围,没有

明确声明它是全局的,但在访问

类似情况下的列表时却没有。



关于这个问题已经有了很长的篇幅。我想我理解它现在是
。这是我的解释。


忽略本练习的嵌套范围,对象的引用(即

变量名)可以存在于本地命名空间或全局

命名空间。 Python首先在本地命名空间中查找,如果没有找到,则
在全局命名空间中查找。


在函数中分配的任何名称都将自动视为

存在于本地命名空间中,除非用全局

语句覆盖。


语句''m = m + 1 '',由于m被分配到LHS,它被认为是本地的b $ b,但由于m在RHS上还没有值,你

得到未绑定的本地错误。


使用语句''n [0] = n [0] + 1'',n未被分配,因为它是

是可变的。因此Python在全局命名空间中查找,在那里找到$
并成功使用它。


我的2c


Frank Millman




Frank Millman写道:


Paddy写道:




我想弄清楚为什么我在访问

时会收到UnboundLocalError int来自int在全局范围内的函数,没有

明确地声明它是全局的,但在访问

类似情况下的列表时却没有。



使用语句''m = m + 1'',因为m被分配给LHS,它被视为
被认为是是本地的,但由于m在RHS上还没有值,你

得到未绑定的本地错误。


语句''n [0 ] = n [0] + 1'',n未被分配,因为它是
是可变的。因此Python在全局命名空间中查找,在那里找到$
并成功使用它。


我的2c


Frank Millman



所以,用来解释我的理解:


声明:''n [0] = n [0] + 1''它是由

名称n引用的对象,而不是n本身,因此n不是

''由作业的LHS标记为''作为局部变量。


谢谢弗兰克。现在一切都很清楚:-)


Frank Millmanaécrit:


Paddy写道:


>>
我试图弄清楚为什么在从一个函数访问一个
int时我得到UnboundLocalError int处于全局范围,没有明确地将其声明为全局但在类似情况下访问列表时没有。




关于这一点,我们有一个很长的线索。我想我理解它现在是
。这是我的解释。


忽略本练习的嵌套范围,对象的引用(即

变量名)可以存在于本地命名空间或全局

命名空间。 Python首先在本地命名空间中查找,如果没有找到,则
在全局命名空间中查找。


在函数中分配的任何名称都将自动视为

存在于本地命名空间中,除非被全局

语句覆盖。



这个甚至本地绑定依次是在另一个

访问该名称之后,即:


g = 0

def fun():

x = g#UnboundLocalError这里

g + = 1

返回x


使用语句''m = m + 1'',因为在LHS上分配了m,它是

被认为是本地的,但由于m在RHS上还没有值,你

得到Unbound Local Error。



正确


语句''n [0] = n [0] + 1' ',n未分配给,



正确


因为它

是可变的。



n实际上是可变的,但这完全无关紧要。在你的

片段中,n不是分配给,而是变异。 (即调用状态修改

方法)。片段:


n [0] = n [0] + 1




$的语法糖b $ b n .__ setitem __(0,n .__ getitem __(0)+ 1)


IOW,这只是方法调用n。


Hi,
I am trying to work out why I get UnboundLocalError when accessing an
int from a function where the int is at the global scope, without
explicitly declaring it as global but not when accessing a list in
similar circumstances.

The documentation: http://docs.python.org/ref/naming.html does not give
me enough info to determine why the difference exists as it does not
seem to mention types at all..

The code:

===== scope_and_type.py =======
m = 0
n = [0]

def int_access0():
m = m + 1
return m
def int_access1():
m += 1
return m
def list_access0():
n[0] = n[0] + 1
return n
def list_access1():
n[0] += 1
return n

try:
print "\nint_access0:", int_access0()
except UnboundLocalError, inst:
print " ERROR:\n", inst
try:
print "\nint_access1:", int_access1()
except UnboundLocalError, inst:
print " ERROR:\n", inst
try:
print "\nlist_access0:", list_access0()
except UnboundLocalError, inst:
print " ERROR:\n", inst
try:
print "\nlist_access1:", list_access1()
except UnboundLocalError, inst:
print " ERROR:\n", inst
print "\n (m,n) = ", (m,n)
p = (0,)
def tuple_access():
return p[0]
try:
print "\ntuple_acces:", tuple_access()
except UnboundLocalError, inst:
print " ERROR:\n", inst
print "\n p = ", p

===== END scope_and_type.py =======

The output:

>>>

int_access0: ERROR:
local variable ''m'' referenced before assignment

int_access1: ERROR:
local variable ''m'' referenced before assignment

list_access0: [1]

list_access1: [2]

(m,n) = (0, [2])

tuple_acces: 0

p = (0,)

>>>

解决方案


Paddy wrote:

Hi,
I am trying to work out why I get UnboundLocalError when accessing an
int from a function where the int is at the global scope, without
explicitly declaring it as global but not when accessing a list in
similar circumstances.

There has just been a long thread about this. I think I understand it
now. Here is my explanation.

Ignoring nested scopes for this exercise, references to objects (i.e.
variable names) can exist in the local namespace or the global
namespace. Python looks in the local namespace first, and if not found
looks in the global namespace.

Any name assigned to within the function is automatically deemed to
exist in the local namespace, unless overridden with the global
statement.

With the statement ''m = m + 1'', as m is assigned to on the LHS, it is
deemed to be local, but as m does not yet have a value on the RHS, you
get Unbound Local Error.

With the statement ''n[0] = n[0] + 1'', n is not being assigned to, as it
is mutable. Therefore Python looks in the global namespace, finds n
there, and uses it successfully.

My 2c

Frank Millman



Frank Millman wrote:

Paddy wrote:

Hi,
I am trying to work out why I get UnboundLocalError when accessing an
int from a function where the int is at the global scope, without
explicitly declaring it as global but not when accessing a list in
similar circumstances.


With the statement ''m = m + 1'', as m is assigned to on the LHS, it is
deemed to be local, but as m does not yet have a value on the RHS, you
get Unbound Local Error.

With the statement ''n[0] = n[0] + 1'', n is not being assigned to, as it
is mutable. Therefore Python looks in the global namespace, finds n
there, and uses it successfully.

My 2c

Frank Millman

So, to paraphrase to test my understanding:

in the statement: '' n[0] = n[0] + 1'' it is the object referenced by the
name n that is being assigned to rather than n itself, so n is not
''tagged'' as a local variable by the LHS of the assignment.

Thanks Frank. all is is now clear :-)


Frank Millman a écrit :

Paddy wrote:

>>Hi,
I am trying to work out why I get UnboundLocalError when accessing an
int from a function where the int is at the global scope, without
explicitly declaring it as global but not when accessing a list in
similar circumstances.



There has just been a long thread about this. I think I understand it
now. Here is my explanation.

Ignoring nested scopes for this exercise, references to objects (i.e.
variable names) can exist in the local namespace or the global
namespace. Python looks in the local namespace first, and if not found
looks in the global namespace.

Any name assigned to within the function is automatically deemed to
exist in the local namespace, unless overridden with the global
statement.

And this even of the local bindings sequentially comes after another
access to the name, ie:

g = 0

def fun():
x = g # UnboundLocalError here
g += 1
return x

With the statement ''m = m + 1'', as m is assigned to on the LHS, it is
deemed to be local, but as m does not yet have a value on the RHS, you
get Unbound Local Error.

Right

With the statement ''n[0] = n[0] + 1'', n is not being assigned to,

Right

as it
is mutable.

n is effectively mutable, but this is totally irrelevant. In your
snippet, n is not ''assigned to'', it''s "mutated" (ie a state-modifying
method is called). The snippet:

n[0] = n[0] + 1

is syntactic sugar for

n.__setitem__(0, n.__getitem__(0) + 1)

IOW, it''s just method calls on n.


这篇关于范围,类型和UnboundLocalError的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆