Arr .__ len __ () Python'da bir dizinin uzunluğunu almanın tercih edilen yolu mudur?


727

In Python , elemanların sayısını almak için aşağıdaki tek yol mu?

arr.__len__()

Eğer öyleyse, neden garip sözdizimi?

Yanıtlar:


1228
my_list = [1,2,3,4,5]
len(my_list)
# 5

Aynı tuples için çalışır:

my_tuple = (1,2,3,4,5)
len(my_tuple)
# 5

Ve sadece karakter dizisi olan dizeler:

my_string = 'hello world'
len(my_string)
# 11

Bu şekilde kasıtlı olarak yapıldı , böylece listeler, tuples ve diğer kap türleri veya yinelenebilirlerin herkese açık bir şekilde genel bir .length()yöntem uygulaması gerekmiyordu , bunun yerine sadece len()'sihirli' __len__()yöntemi uygulayan her şeyi kontrol edebilirsiniz .

Elbette, bu gereksiz görünebilir, ancak uzunluk kontrolü uygulamaları aynı dilde bile önemli ölçüde değişebilir. Bir koleksiyon türünün bir .length()yöntem kullandığını, başka bir tür ise bir .lengthözelliği kullandığını, başka bir türün kullanıldığını görmek nadir değildir .count(). Dil düzeyinde bir anahtar kelimeye sahip olmak, tüm bu türler için giriş noktasını birleştirir. Bu nedenle, öğe listesi olarak düşünemeyeceğiniz nesneler bile yine de uzunluk kontrolünden geçirilebilir. Bu, dizeleri, kuyrukları, ağaçları vb. İçerir.

İşlevsel doğası len()da işlevsel programlama stillerine iyi bir uyum sağlar.

lengths = map(len, list_of_containers)

8
len () bir dil komutudur, __len __ () kapsayıcı türlerinde kullanılan bir yöntemdir.
Soviut

33
len () küresel, yerleşik bir işlevdir; __len __ (), nesnenin uygulayabileceği bir yöntemdir. len (foo) genellikle foo .__ len __ () 'i çağırır.
Tim Lesher

13
Len () sağlayarak her kapsayıcıya bir .length () yöntemi uygulamak zorunda değildir, ancak her tür yine de len () tarafından çağrılan bir __len __ () yöntemi uygularsa bu nasıl farklıdır? Farklı kap tipleri len () ile farklı mı ele alınır?
Simon B. Jensen

10
@Simon: ".length () 'i uygulamak zorunda değilsiniz" biraz kafa karıştırıcıdır. Konteyner türlerinin hala uzunluklarını döndürmek için bir yöntem uygulaması gerekir; önemli olan, standartlaştırılmış bir protokol olmasıdır, her tür için aradığınız özel bir yöntem değildir. Çift alt çizgi bunu gösterir.
Carl Meyer

16
Carl Meyer ile aynı fikirdeyim - bunun bir kamu .length () yönteminin "açıkça uygulanması gerekmediğini" yanıltıcı ve temel anlamıyla yanlış olduğunu söyleyerek katılıyorum. Her şey len'i uygulamak zorunda kalacak ve len işlevini atlatarak her zaman istedikleri adda kendi uzunluk yöntemlerini uygulayabilir. Gerçekten bunu Guido'nun dünyayı nasıl gördüğüne uyan keyfi bir tuhaflık olarak görüyorum. Muhtemelen herhangi bir evrensel akıl yürütmeyle ilgisi yoktur.
BT

52

Mantıklı olan herhangi bir şeyin uzunluğunu alma şekliniz (liste, sözlük, grup, dize, ...) lenonu çağırmaktır .

l = [1,2,3,4]
s = 'abcde'
len(l) #returns 4
len(s) #returns 5

"Garip" sözdizimi nedeni, içsel piton çevirir olduğunu len(object)içine object.__len__(). Bu, herhangi bir nesne için geçerlidir. Yani, bir sınıf tanımlıyorsanız ve bunun bir uzunluğa sahip olması mantıklıysa, sadece bir __len__()yöntem tanımlayın ve sonra lenbu örnekleri çağırabilirsiniz .


23

Python kullanan ördek yazarak : bir nesne nedir umursamıyor olduğu sürece el altında durumunuza uygun arayüze sahip olarak. Bir nesnede yerleşik işlev len () öğesini çağırdığınızda, aslında dahili __len__ yöntemini çağırırsınız. Özel bir nesne bu arabirimi uygulayabilir ve nesne kavramsal olarak bir sıra olmasa bile len () yanıtı döndürür.

Arabirimlerin tam listesi için buraya bakın: http://docs.python.org/reference/datamodel.html#basic-customization


23

Herhangi bir python nesnesinin uzunluğunu almanın tercih edilen yolu, nesneyi lenişleve argüman olarak iletmektir. Dahili olarak, python daha sonra __len__iletilen nesnenin özel yöntemini çağırmaya çalışır .


22

Sadece kullanın len(arr):

>>> import array
>>> arr = array.array('i')
>>> arr.append('2')
>>> arr.__len__()
1
>>> len(arr)
1

10

len(arr) dizinin uzunluğunu öğrenmek için önceki yanıtlarda önerildiği gibi kullanabilirsiniz . 2B dizinin boyutlarını istiyorsanız, arr.shapeyükseklik ve genişlik değerlerini kullanabilirsiniz


7

len(list_name)işlevi listeyi parametre olarak alır ve listenin __len__()işlevini çağırır .


1

Python, diğer adamların söylediği gibi, kullanıcıların tutarlılık len()yerine kullanmasını önerir __len__(). Ancak, başka yararları da vardır:

İçin bazı yerleşik gibi türleri list, str, bytearrayve benzeri, bir Cython uygulamasılen() bir kısayol alır. Doğrudan çağrıdan ob_sizedaha hızlı bir C yapısında döndürür __len__().

Bu tür ayrıntılarla ilgileniyorsanız, Luciano Ramalho'nun "Fluent Python" adlı kitabını okuyabilirsiniz. İçinde birçok ilginç detay var ve Python'u daha derinden anlamanıza yardımcı olabilir.

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.