In Python 3.5.0 this code:
a = (1,2)
class Foo(object):
b = (3,4)
c = tuple((i,j) for j in b for i in a)
d = tuple((i,j) for i in a for j in b)
produces:
Traceback (most recent call last):
File "genexprtest.py", line 2, in <module>
class Foo(object):
File "genexprtest.py", line 5, in Foo
d = tuple((i,j) for i in a for j in b)
File "genexprtest.py", line 5, in <genexpr>
d = tuple((i,j) for i in a for j in b)
NameError: name 'b' is not defined
Why do I get this error? And why do I not get this error on the previous line?
The Python "NameError: name is not defined" occurs when we try to access a variable or function that is not defined or before it is defined. To solve the error, make sure you haven't misspelled the variable's name and access it after it has been declared.
What Is a NameError in Python? In Python, the NameError occurs when you try to use a variable, function, or module that doesn't exist or wasn't used in a valid way. Some of the common mistakes that cause this error are: Using a variable or function name that is yet to be defined.
A syntax error occurs when a programmer writes an incorrect line of code. Most syntax errors involve missing punctuation or a misspelled name.
This is because the expression for i in a
has a local variable scope, and expression for j in b
is inside the scope, thus, no b
is found.
Actually, if you write c = tuple((i, j) for i in a for j in b)
, it will throw the same exception.
The solution is put b
into scope of class definition (as you already did) and refer it by self.b
.
I spent ages experimenting and I have a theory about why you're getting this error. I'm not certain but this does explain why it works for c
and not for d
. I hope this helps you, comment if you disagree :)
def Tuple(this):
print(a) # this always works
try:
print(b) # this always gives an error
except NameError:
print("...b is not defined")
try:
return tuple(this) # this only gives an error for d and e
except NameError:
print("...couldn't make it a tuple")
a = (1,2)
class Foo(object):
b = (3,4)
c = Tuple((i,j) for j in b for i in a)
d = Tuple((i,j) for i in a for j in b)
e = Tuple((i,j,k) for i in a for j in b for k in (5, 6))
f = Tuple((i,j,k) for j in b for i in (5, 6) for k in a)
print("\nc:", c,"\nd:", d,"\ne:", e,"\nf:", f)
What happened: every time I called the Tuple()
function, b
was not defined, but a
was always defined. This explains why you get an error for d
and e
but it doesn't explain why c
and f
work even though b
is 'not defined'
My theory: The first for
loop is calculated before the whole thing is converted into a tuple. For example, if you tried to do this: Tuple((a, b, c) for a in loop1, for b in loop2 for c in loop3)
, in the Foo class it would calculate for a in loop1
first, then it would move to the foo and calculate the loops 2 and 3.
In summary:
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With