On 5/8/18 3:55 AM, Alexey Muranov wrote:
Sorry, i was confused.  I would say that this mostly works as expected, though the difference between

   x = 42

   class C:
       x = x  # Works

and

   def f2(a):
       class D:
           a = a  # Does not work <<<<<
       return D

is still surprising to me.

Otherwise, probably the solution with

   def f(a):
       _a = a
       class D:
           a = _a
       return D

is good enough, if Python does not allow to refer "simultaneously" to variables from different scopes if they have the same name.

Alexey.

I'm curious to see the real code you're writing that uses this style of class creation.  It feels like there might be an easier way to achieve your goal.

--Ned.


On Tue, 8 May, 2018 at 12:21 AM, Alexey Muranov <alexey.mura...@gmail.com> wrote:
To be more exact, i do see a few workarounds, for example:


   def f4(a):
       b = a
       class D:
           a = b  # Works
       return D

But this is not what i was hoping for.

Alexey.

On Tue, 8 May, 2018 at 12:02 AM, Alexey Muranov <alexey.mura...@gmail.com> wrote:
I have discovered the following bug or problem: it looks like i am forced to choose different names for class attributes and function arguments, and i see no workaround.  Am i missing some special syntax feature ?

Alexey.

---
x = 42

class C1:
   y = x  # Works

class C2:
   x = x  # Works

# ---
def f1(a):
   class D:
       b = a  # Works
   return D

def f2(a):
   class D:
       a = a  # Does not work <<<<<
   return D

def f3(a):
   class D:
       nonlocal a
       a = a  # Does not work either <<<<<
   return D

# ---
def g1(a):
   def h():
       b = a  # Works
       return b
   return h

def g2(a):
   def h():
       a = a  # Does not work (as expected)
       return a
   return h

def g3(a):
   def h():
       nonlocal a
       a = a  # Works
       return a
   return h

# ---
if __name__ == "__main__":
   assert C1.y == 42
   assert C2.x == 42

   assert f1(13).b == 13

   try:
       f2(13)  # NameError
   except NameError:
       pass
   except Exception as e:
       raise Exception( 'Unexpected exception raised: '
                        '{}'.format(type(e).__name__) )
   else:
       raise Exception('No exception')

   try:
       f3(13).a  # AttributeError
   except AttributeError:
       pass
   except Exception as e:
       raise Exception( 'Unexpected exception raised: '
                        '{}'.format(type(e).__name__) )
   else:
       raise Exception('No exception')

   assert g1(13)() == 13

   try:
       g2(13)()  # UnboundLocalError
   except UnboundLocalError:
       pass
   except Exception as e:
       raise Exception( 'Unexpected exception raised: '
                        '{}'.format(type(e).__name__) )
   else:
       raise Exception('No exception')

   assert g3(13)() == 13




--
https://mail.python.org/mailman/listinfo/python-list

Reply via email to