2009-10-15 6 views
14

J'ai une chaîne de données avec le format suivant: xpos-ypos-zoom (ie 8743-12083-15) que je veux séparer et stocker dans les variables xpos, ypos et zoom. Puisque j'ai besoin de faire des calculs avec ces nombres, je voudrais les convertir en entiers dès le début. À l'heure actuelle, la façon dont je fais est avec le code suivant:Un moyen efficace de convertir les chaînes de la fonction split à ints en Python

file = '8743-12083-15' 
xval, yval, zoom = file.split("-") 
xval = int(xval) 
yval = int(yval) 

Il me semble qu'il devrait y avoir un moyen plus efficace de le faire. Des idées?

Répondre

37

Ma suggestion originale avec une compréhension de la liste.

test = '8743-12083-15' 
lst_int = [int(x) for x in test.split("-")] 

EDIT:

Quant à ce qui est le plus efficace (cpu-cyclewise) est quelque chose qui doit toujours être testé. Certains tests rapides sur mon installation Python 2.6 indiquent carte est probablement le candidat le plus efficace ici (construction d'une liste d'entiers à partir d'une chaîne de valeur divisée). Notez que la différence est si faible que cela ne compte pas vraiment jusqu'à ce que vous faites cela des millions de fois (et il est un goulot d'étranglement prouvé) ...

def v1(): 
return [int(x) for x in '8743-12083-15'.split('-')] 

def v2(): 
return map(int, '8743-12083-15'.split('-')) 

import timeit 
print "v1", timeit.Timer('v1()', 'from __main__ import v1').timeit(500000) 
print "v2", timeit.Timer('v2()', 'from __main__ import v2').timeit(500000) 

> output v1 3.73336911201 
> output v2 3.44717001915 
+3

carte est généralement plus rapide que la compréhension lors de l'utilisation d'une fonction intégrée, et plus lente si vous utilisez une fonction définie par l'utilisateur (y compris lambda) –

5

Vous pouvez map la fonction int sur chaque sous-chaîne, ou utilisez un list comprehension:

>>> file = '8743-12083-15' 
>>> list(map(int, file.split('-'))) 
[8743, 12083, 15] 
>>> [int(d) for d in file.split('-')] 
[8743, 12083, 15] 

Dans ce qui précède l'appel à list n'est pas nécessaire, à moins de travailler avec Python 3.x. (En Python 2.x map retourne une liste, dans 3.x Python retourne un générateur.)

attribution directe est également possible aux trois variables (dans ce cas, une compréhension generator expression au lieu d'une liste fera):

>>> xval, yval, zval = (int(d) for d in file.split('-')) 
>>> xval, yval, zval 
(8743, 12083, 15) 
+0

avez-vous besoin liste() appeler? map renvoie une liste ... –

+2

Pas en Python 3 –

+0

intéressant, une chose de plus que j'ai appris sur p3k: D –

10

efficace comme dans moins de lignes de code?

(xval,yval,zval) = [int(s) for s in file.split('-')] 
+1

I D 'affirmer que cette réponse est efficace comme dans "le plus facile à coder et à passer à d'autres choses plus importantes, et à comprendre quand je reviendrai plus tard". Essayer de gagner des microsecondes de performance à partir de cette ligne de code particulière est clairement un détour dans le Tarpit de l'optimisation inutile. – PaulMcG

+0

Je suis généralement d'accord et c'est exactement pourquoi je ne l'ai pas brossé (bien que je sois conscient des expressions de générateur et similaires). Mais, comme il s'agit de * trois * éléments, il peut aussi bien être laissé que –

4

Note: vous pouvez choisir un autre nom file comme ombres l'buildtin

cela fonctionne en Python 2 et 3


xval,yval,zval = map(int,file.split('-')) 
Questions connexes