Her liste öğesinde int () işlevi çağrılsın mı?


184

Ben gibi sayısal dizeleri olan bir liste var:

numbers = ['1', '5', '10', '8'];

Her liste öğesini tamsayıya dönüştürmek istiyorum, bu yüzden şöyle görünecektir:

numbers = [1, 5, 10, 8];

Ben böyle bir döngü kullanarak yapabilirdi:

new_numbers = [];
for n in numbers:
    new_numbers.append(int(n));
numbers = new_numbers;

Bu kadar çirkin olmalı mı? Eminim kod bir satırda bunu yapmak için daha pythonic bir yolu vardır. Lütfen bana yardım edin.


1
Hangi Python sürümünü kullanıyorsunuz?
Mark Byers

Yanıtlar:



131

Python 2.x'te başka bir yaklaşım kullanmaktır map:

numbers = map(int, numbers)

Not: Python 3.x'te map, isterseniz bir listeye dönüştürebileceğiniz bir harita nesnesi döndürür:

numbers = list(map(int, numbers))

11
Python 3.x'te, mapliste yerine yineleyici döndürdüğünden listeye ihtiyaç varmış gibi yazılması list(map(int, numbers))gerekir.
kennytm

2
Bence şu an liste kavrama yaklaşımı biraz daha fazla tercih ediliyor.
extraneon

3
@extraneon: Evet ... ya da belki ne için kullanacağınıza bağlı olarak liste yerine bir jeneratör kullanmayı düşünün. Bir jeneratörün avantajı, tüm elemanlara bakmanız gerekmiyorsa, bunları önceden hesaplamak için zaman kaybetmek zorunda kalmamanızdır.
Mark Byers

4
Python 2.7.2 altında zamana göre ölçüldü: LC: 3.578153133392334, harita: 4.9065070152282715
AJJ

1
@AJJ: mapdaha yüksek kurulum yüküne sahiptir, ancak referans yorumlayıcıda, dönüştürme işlevi C'de uygulanan bir Python yerleşik işleviyse , öğe başına maliyeti daha düşüktür. Sadece dört değerin olduğu bir girişte test yapmak, ölçeklendirme hakkında yararlı bilgiler sağlamaz. Bununla birlikte, kendi testlerimde (Py2.7.12 ve Py3.5.2'de, ikincisi list()ambalajlı), Py2 mapdört element girişi için bile kazandı ve Py3'te sadece küçük bir farkla kayboldu; Testlerinizin listcomps lehine çarpık olduğundan şüpheleniyorum.
ShadowRanger

21

sadece bir nokta,

numbers = [int(x) for x in numbers]

liste kavraması daha doğal,

numbers = map(int, numbers)

daha hızlı.

Muhtemelen bu çoğu durumda önemli olmayacaktır

Yararlı okuma: LP vs harita


6
Sayı = harita (int, sayı) olmamalı mı?
Karan

9

Bu tam sayıları bir işleve veya yönteme aktarmak istiyorsanız, bu örneği göz önünde bulundurun:

sum(int(x) for x in numbers)

Bu yapı kasıtlı olarak adamk tarafından bahsedilen liste kavrayışlarına oldukça benzer. Köşeli parantez olmadan, buna jeneratör ifadesi denir ve bir argüman listesini bir yönteme geçirmenin çok bellek tasarruflu bir yoludur. Burada iyi bir tartışma var: Jeneratör İfadeleri ve Liste Anlama


4

Python 3'te yapmanın başka bir yolu:

numbers = [*map(int, numbers)]


1
Bunu açıklayabilir misin? Bu sözdizimine aşina değilim. Teşekkürler!
abalter

1
Paketten çıkarma bağımsız değişkenler listesini kullanıyorum ( docs.python.org/3/tutorial/… )
zhukovgreen

Aha, bir python 3 şey. []Bir tartışma listesi almak garip görünüyor . Ve bir iteratörü argüman listesi olarak geçirebileceğinizi bilmiyordum. Yapmayı düşünürdüm number = list(map(int, numbers)). Ama açıklama için teşekkürler!
abalter

3

Diğer yol,

for i, v in enumerate(numbers): numbers[i] = int(v)

6
OP dedi pythonic
SilentGhost

3
İşlemi yalnızca listedeki bazı öğelerde yürütmek istiyorsanız, bu şekilde çok kullanışlıdır. Bu konudaki soru ile ilgili değildir, ancak yararlı olduğu durumlar olabilir
Dikla

1

Cevapları pekiştirdiğimi ve bazı timeitsonuçlar gösterdiğimi düşündüm .

Python 2 bu konuda oldukça kötü, ama mapkavrayıştan biraz daha hızlı.

Python 2.7.13 (v2.7.13:a06454b1afa1, Dec 17 2016, 20:42:59) [MSC v.1500 32 bit (Intel)] on win32
Type "copyright", "credits" or "license()" for more information.
>>> import timeit
>>> setup = """import random
random.seed(10)
l = [str(random.randint(0, 99)) for i in range(100)]"""
>>> timeit.timeit('[int(v) for v in l]', setup)
116.25092001434314
>>> timeit.timeit('map(int, l)', setup)
106.66044823117454

Python 3 kendi başına 4 kat daha hızlıdır, ancak mapjeneratör nesnesini bir listeye dönüştürmek hala anlamadan daha hızlıdır ve mapjeneratörü paketinden çıkararak liste oluşturmak (teşekkürler Artem!) Hala daha hızlıdır.

Python 3.6.1 (v3.6.1:69c0db5, Mar 21 2017, 17:54:52) [MSC v.1900 32 bit (Intel)] on win32
Type "copyright", "credits" or "license()" for more information.
>>> import timeit
>>> setup = """import random
random.seed(10)
l = [str(random.randint(0, 99)) for i in range(100)]"""
>>> timeit.timeit('[int(v) for v in l]', setup)
25.133059591551955
>>> timeit.timeit('list(map(int, l))', setup)
19.705547827217515
>>> timeit.timeit('[*map(int, l)]', setup)
19.45838406513076

Not: Python 3'te, 4 öğenin kavrama noktası olduğu anlaşılmaktadır (Python 2'de 3), anlaşmanın biraz daha hızlı olduğu, ancak jeneratörün paketinin açılması hala 1'den fazla öğeye sahip listelerin her ikisinden de daha hızlıdır.

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.