50 votes

Le moyen le plus rapide d'échanger des éléments dans la liste Python

Existe-t-il un moyen plus rapide d’échanger deux éléments de liste en Python que

 L[a], L[b] = L[b], L[a]
 

ou devrais-je recourir à Cython ou Weave ou similaires?

132voto

Ignacio Vazquez-Abrams Points 312628

On dirait que le compilateur Python optimise le tuple temporaire avec cette construction:

code:

 import dis

def swap1():
  a=5
  b=4
  a, b = b, a

def swap2():
  a=5
  b=4
  c = a
  a = b
  b = c

print 'swap1():'
dis.dis(swap1)
print 'swap2():'
dis.dis(swap2)
 

sortie:

 swap1():
  6           0 LOAD_CONST               1 (5)
              3 STORE_FAST               0 (a)

  7           6 LOAD_CONST               2 (4)
              9 STORE_FAST               1 (b)

  8          12 LOAD_FAST                1 (b)
             15 LOAD_FAST                0 (a)
             18 ROT_TWO             
             19 STORE_FAST               0 (a)
             22 STORE_FAST               1 (b)
             25 LOAD_CONST               0 (None)
             28 RETURN_VALUE        
swap2():
 11           0 LOAD_CONST               1 (5)
              3 STORE_FAST               0 (a)

 12           6 LOAD_CONST               2 (4)
              9 STORE_FAST               1 (b)

 13          12 LOAD_FAST                0 (a)
             15 STORE_FAST               2 (c)

 14          18 LOAD_FAST                1 (b)
             21 STORE_FAST               0 (a)

 15          24 LOAD_FAST                2 (c)
             27 STORE_FAST               1 (b)
             30 LOAD_CONST               0 (None)
             33 RETURN_VALUE        
 

Deux charges, une ROT_TWO et deux sauvegardes, contre trois charges et trois sauvegardes. Il est peu probable que vous trouviez un mécanisme plus rapide.

3voto

TryPyPy Points 3317

Si vous pouviez publier un exemple de code représentatif, nous pourrions mieux analyser vos options. FWIW, pour le benchmark stupide suivant, je reçois environ 3 fois plus rapidement Shed Skin et 10 fois plus vite avec PyPy .

 from time import time

def swap(L):
    for i in xrange(1000000):
        for b, a in enumerate(L):
            L[a], L[b] = L[b], L[a]

def main():
    start = time()
    L = list(reversed(range(100)))
    swap(L[:])
    print time() - start
    return L

if __name__ == "__main__":
    print len(main())

# for shedskin:
# shedskin -b -r -e listswap.py && make
# python -c "import listswap; print len(listswap.main())"
 

0voto

ismail Points 19146

C'est le moyen le plus rapide car il n'utilise pas de variable temporaire.

-5voto

J'ai trouvé cette méthode comme le moyen le plus rapide d'échanger deux nombres:

 mylist   = [11,23,5,8,13,17];
first_el = mylist.pop(0)
last_el  = mylist.pop(-1)
mylist.insert(0, last_el)  
mylist.append(first_el)
 

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X