0

I'm running into a silly issue that I can't figure out. If I assign an attribute to a lambda function via setattr in a for loop, it will assign all the attributes the same value as that which was passed in the last iteration of the loop. Can anyone shed some light on this?

class bee(object):
    def __init__(self):
        def say_my_name (self, name):
            return name

        setattr(bee, f'Jim_name', property(lambda self: say_my_name(self, 'Jim')))
        setattr(bee, f'Jill_name', property(lambda self: say_my_name(self, 'Jill')))

        for name in ['Jake', 'Jordan']:
            setattr(bee, f'{name}_name', property(lambda self: say_my_name(self, name)))

buzz = bee()

print(buzz.Jim_name)
# >Jim

print(buzz.Jill_name)
# >Jill

print(buzz.Jake_name)
# >Jordan
# Should be Jake!

print(buzz.Jordan_name)
# >Jordan
  • 1
    `name` is a free variable; lookup doesn't occur until the getter is called, not when the getter is defined. – chepner Feb 10 '21 at 21:04
  • 1
    Why are you repeatedly (re)creating instance-specific properties every time `__init__` is called, anyway? – chepner Feb 10 '21 at 21:05
  • Because in the full code the attributes are dynamically created and the property does a lot more fancy stuff. – Wyko ter Haar Feb 10 '21 at 21:13
  • 1
    Do you ever create more than once instance of `bee`? If you do, you are unnecessarily recreating the properties each time you create an instance. If not, I wonder if you *should* be. – chepner Feb 10 '21 at 21:23

0 Answers0