Toon posts:

[Python] Problemen met referenties in Lambda functie

Pagina: 1
Acties:

Onderwerpen

Vraag


Acties:
  • 0Henk 'm!

  • cosmo50
  • Registratie: Mei 2011
  • Laatst online: 02-12-2022
Ik loop tegen iets aan wat, als ik het internet zo zie, vaker een probleem is. Ik probeer voor verschillende datapunten een hele rits aan lambda functies op te bouwen, om dan in een later stadium deze functies te kunnen gebruiken om on-the-fly data te genereren. Een voorbeeld:

Python:
1
2
3
4
5
6
7
8
9
10
11
a = range(0, 3)
names = ['A', 'B', 'C']

example = {}
for idx, name in enumerate(names):
    changing_var = a[idx]
    example[name] = lambda x: x*changing_var

print(example['A'](5))  # Verwacht 0*5 = 0
print(example['B'](5))  # Verwacht 1*5 = 5
print(example['C'](5))  # Verwacht 2*5 = 10


Zoals te zien, wordt er in de lambda functie verwezen naar een getal welke verandert per iteratie. Zoals op stackoverflow te vinden, ligt dit probleem zoals verwacht in de veranderende referentie per iteratie. Echter, met de verschillende opties die daar worden genoemd (hard-coden, volgorde veranderen, verschillende variabele namen, verschillende namespaces gebruiken), verlies ik aardig wat leesbaarheid (denk ik?), en vooral flexibiliteit.

Een aardige omweg lijkt mij om op de een-of-andere manier de variabelen tóch te forceren om gekopieerd te worden, en de reference naar deze nieuwe variabele op te slaan in de lambda. Na verschillende pogingen met deepcopy's e.d., kom ik niet verder.

Denk ik te lastig, en is het toch een betere optie om volledig om het probleem heen te werken? Of zie ik iets over het hoofd?

Beste antwoord (via cosmo50 op 24-05-2022 17:00)


  • luukvr
  • Registratie: Juni 2011
  • Niet online
Waarom zijn de oplossingen in die stackoverflow post niet goed voor jou?

De helper functie oplossing daar lijkt me prima flexibel en leesbaar.

Python:
1
2
3
4
5
6
7
8
9
a = range(0, 3)
names = ['A', 'B', 'C']

def helper_function(name):
    return lambda x: x * a[names.index(name)]

print(helper_function('A')(5))  # Verwacht 0*5 = 0
print(helper_function('B')(5))  # Verwacht 1*5 = 5
print(helper_function('C')(5))  # Verwacht 2*5 = 10

Alle reacties


Acties:
  • Beste antwoord
  • 0Henk 'm!

  • luukvr
  • Registratie: Juni 2011
  • Niet online
Waarom zijn de oplossingen in die stackoverflow post niet goed voor jou?

De helper functie oplossing daar lijkt me prima flexibel en leesbaar.

Python:
1
2
3
4
5
6
7
8
9
a = range(0, 3)
names = ['A', 'B', 'C']

def helper_function(name):
    return lambda x: x * a[names.index(name)]

print(helper_function('A')(5))  # Verwacht 0*5 = 0
print(helper_function('B')(5))  # Verwacht 1*5 = 5
print(helper_function('C')(5))  # Verwacht 2*5 = 10

Acties:
  • 0Henk 'm!

  • Ben(V)
  • Registratie: December 2013
  • Laatst online: 15:58
Of gewoon een enkele lambda zoals dit?
code:
1
2
3
4
5
6
names = ['A', 'B', 'C']
example = lambda x,y: x*y

print (example(names.index('A'), 5))
print (example(names.index('B'), 5))
print (example(names.index('C'), 5))

All truth passes through three stages: First it is ridiculed, second it is violently opposed and third it is accepted as being self-evident.


Acties:
  • 0Henk 'm!

  • cosmo50
  • Registratie: Mei 2011
  • Laatst online: 02-12-2022
Ja, die helper lijkt inderdaad toch het voor elkaar te krijgen. Denk dat ik het initieel verkeerd interpreteerde. Dank!


Tweakers maakt gebruik van cookies

Tweakers plaatst functionele en analytische cookies voor het functioneren van de website en het verbeteren van de website-ervaring. Deze cookies zijn noodzakelijk. Om op Tweakers relevantere advertenties te tonen en om ingesloten content van derden te tonen (bijvoorbeeld video's), vragen we je toestemming. Via ingesloten content kunnen derde partijen diensten leveren en verbeteren, bezoekersstatistieken bijhouden, gepersonaliseerde content tonen, gerichte advertenties tonen en gebruikersprofielen opbouwen. Hiervoor worden apparaatgegevens, IP-adres, geolocatie en surfgedrag vastgelegd.

Meer informatie vind je in ons cookiebeleid.

Sluiten

Toestemming beheren

Hieronder kun je per doeleinde of partij toestemming geven of intrekken. Meer informatie vind je in ons cookiebeleid.

Functioneel en analytisch

Deze cookies zijn noodzakelijk voor het functioneren van de website en het verbeteren van de website-ervaring. Klik op het informatie-icoon voor meer informatie. Meer details

janee

    Relevantere advertenties

    Dit beperkt het aantal keer dat dezelfde advertentie getoond wordt (frequency capping) en maakt het mogelijk om binnen Tweakers contextuele advertenties te tonen op basis van pagina's die je hebt bezocht. Meer details

    Tweakers genereert een willekeurige unieke code als identifier. Deze data wordt niet gedeeld met adverteerders of andere derde partijen en je kunt niet buiten Tweakers gevolgd worden. Indien je bent ingelogd, wordt deze identifier gekoppeld aan je account. Indien je niet bent ingelogd, wordt deze identifier gekoppeld aan je sessie die maximaal 4 maanden actief blijft. Je kunt deze toestemming te allen tijde intrekken.

    Ingesloten content van derden

    Deze cookies kunnen door derde partijen geplaatst worden via ingesloten content. Klik op het informatie-icoon voor meer informatie over de verwerkingsdoeleinden. Meer details

    janee