Stavo scrivendo un gioco tic-tac-toe e utilizzando un Enum per rappresentare i tre risultati - lose
, draw
e win
. Ho pensato che sarebbe stato meglio usare le stringhe ("lose", "win", "draw")
per indicare questi valori. Ma usare le enumerate mi ha dato un notevole successo nelle prestazioni.Come usare le enumerazioni di Python 3.4 senza un rallentamento significativo?
Ecco un esempio minimo, in cui faccio semplicemente riferimento a Result.lose
o alla stringa letterale lose
.
import enum
import timeit
class Result(enum.Enum):
lose = -1
draw = 0
win = 1
>>> timeit.timeit('Result.lose', 'from __main__ import Result')
1.705788521998329
>>> timeit.timeit('"lose"', 'from __main__ import Result')
0.024598151998361573
Questo è molto più lento del semplice riferimento a una variabile globale.
k = 12
>>> timeit.timeit('k', 'from __main__ import k')
0.02403248500195332
Le mie domande sono:
- So che le ricerche globali sono molto più lenti di quanto le ricerche locali in Python. Ma perché le occhiate enum sono ancora peggio?
- In che modo le enumerazioni possono essere utilizzate in modo efficace senza sacrificare le prestazioni? La ricerca di Enum si è rivelata completamente dominante sul runtime del mio programma tic-tac-toe. Potremmo salvare copie locali dell'enum in ogni funzione, o avvolgere tutto in una classe, ma entrambe sembrano imbarazzanti.
Penso che sia probabilmente il recupero degli attributi che è lento. Se fai qualcosa come 'lose = Result.lose' e poi prova contro' lose', sia esso locale o globale, penso che vedrai un aumento misurabile. – Shashank
Grazie, funziona abbastanza bene. Sai perché la ricerca degli attributi è molto più lenta della ricerca globale? So che i locali sono archiviati in un array a lunghezza fissa mentre i globals sono in un ditt, ma qual è l'accordo con gli attributi? –
Non lo so, mi dispiace. E non potrei dirti nulla con certezza senza leggere la fonte CPython. Se dovessi indovinare, direi che gli oggetti sono implementati con array associativi o mappe o qualsiasi altra cosa sotto il cofano (solo una possibilità, non da considerare come un fatto), quindi potrebbe esserci un costo per l'algoritmo di hash utilizzato sui nomi degli attributi che sono come chiavi di stringa per una tabella hash, ma questa è tutta la speculazione. In ogni caso, ora sai come ridurlo al minimo nel caso di ricerche ripetitive. Localizzazione ftw. – Shashank