Python'daki tek alt çizgi “_” değişkeninin amacı nedir?


618

Anlamı nedir _sonra forbu kodu?

if tbh.bag:
   n = 0
   for _ in tbh.bag.atom_set():
      n += 1


5
Sizin durumunuz için, ya len(tbh.bag.atom_set())(döndürülen değerin bir __len__yöntemi varsa) ya dasum(1 for _ in tbh.bag.atom_set())
Nick T

Gelen pylintkukla değişken adları için başka seçeneğin bir önek olan dummy_değişken adını. Bu önek kullanarak pylintyapar pylintbir uyarı çıkarmaz. Ayrıca kukla değişken modelini, pylintgibi şeyleri karşılamak üzere yapılandırabilirsiniz __.
Trevor Boyd Smith

Yanıtlar:


780

_ Python'da 4 ana konvansiyonel kullanıma sahiptir:

  1. Etkileşimli yorumlayıcı oturumunda son yürütülen ifadenin (/ ifadesinin) sonucunu tutmak. Bu emsal standart CPython tercümanı tarafından belirlendi ve diğer tercümanlar da bunu izledi
  2. Aşağıdaki gibi kodda olduğu gibi i18n'deki çeviri araması için (örneğin gettext belgelerine bakın): raise forms.ValidationError(_("Please enter a correct username"))
  3. Genel bir amaç olarak "ıskarta" değişken adı gibi kodda olduğu gibi, (. Kavramsal olarak, atılan ediliyor) bir işlev sonucu o kısmı kasten göz ardı edildiğini göstermek üzere: label, has_label, _ = text.partition(':').
  4. İmzanın sabitlendiği bir işlev tanımının ( defveya birini kullanarak lambda) bir parçası olarak (ör. Geri arama veya üst sınıf API ile), ancak bu özel işlev uygulaması, koddaki gibi tüm parametrelere ihtiyaç duymaz:callback = lambda _: True

(Uzun bir süre için bu cevap sadece ilk üç kullanım örneğini listeledi, ancak dördüncü vaka burada belirtildiği gibi açıkça listelenmeye değecek kadar sık ​​ortaya çıktı )

Sonuncu "değişken değişken veya parametre adı", vakaları çeviri arama kullanım durumu ile çakışabilir, bu nedenle _i18n çevirisi için de kullanan herhangi bir kod bloğunda bir değişken değişken olarak kullanmaktan kaçınmak gerekir (birçok kişi çift alt çizgiyi tercih eder) , __tam da bu nedenle değişken değişkenleri olarak).


19
Bir işlev çağrısında nasıl çalıştığını açıklayabilir misiniz, örneğin: formları yükseltin.ValidationError (_ ("Lütfen doğru bir kullanıcı adı girin")) . Bunu Django kodunda gördüm ve neler olduğu belli değil.
John C

41
Yani kullanım 2 - kural gereği, _uluslararasılaştırma ve yerelleştirme dizesi çeviri aramalarını yapan işlev için kullanılan addır. gettextBu konvansiyonu kuran C kütüphanesi olduğundan eminim .
ncoghlan

43
FWIW, kişisel __olarak ilk iki kullanım durumundan herhangi biriyle çelişmemek için genel çift yönlü değişken olarak kullanmaya başladım.
ncoghlan

14
Ortaya çıkan topluluk sözleşmeleri yetkili kaynaklara sahip olma eğiliminde değildir - sadece zaman içinde ortaya çıkan uygulamaların gözlemleri. FWIW, daha yeni PEP 8 güncellemelerinin ortak yazarlarından biriyim ve cevabım, _2002 yılında profesyonel olarak Python'u kullanmaya başladığımdan beri değişken bir ad olarak kullanıldığını gördüğüm 3 farklı yolu temel alıyor .
ncoghlan

12
Kural esas olarak demet açma için: a, __, c = iterableokuyucuya hemen 3 demet açmadığımızı söyler, ancak sadece ilk ve son değerleri kullanır. Bunun yerine yazarsanız a, b, c = iterable, okuyucu (veya otomatik kod linter) makul tüm bekleyebilirsiniz a, bve cdaha sonra kullanılmak üzere (ve onlar değil, eğer bir hata yerde bir işareti olabilir).
ncoghlan

207

Bu sadece değişken bir isim ve _python'da eğik değişkenler için geleneksel olarak kullanılıyor . Sadece loop değişkeninin aslında kullanılmadığını gösterir.


5
yani son döndürülen değeri göstermiyor mu?
alwbtc

31
@steve sadece bir python kabuğu
Gabi Purcaru

4
Prolog'da _ kullanımına benzer
Matthias

3
Matlab
PatriceG

Açıkça tanımlarsanız _, cpython kabuğunda , önceki ifadenin çıktı değerini tutmayı kalıcı olarak durdurduğunu unutmayın. Bu çok tutarsız görünüyor ve Python lang standartlarının buna değinmesi gerekiyor. Sadece _bir takma ad olarak tanımlamalı ve gerçek bir tanımlayıcı olarak kullanılmasını durdurmalıdırlar.
theferrit32

78

Alt çizgi Python'da " Umurumda Değil " veya " Gerileme " değişkeni _olarak kabul edilir

  • Python yorumlayıcısı, son ifade değerini çağrılan özel değişkene kaydeder _.

    >>> 10 
    10
    
    >>> _ 
    10
    
    >>> _ * 3 
    30
  • Alt çizgi _, belirli değerleri yok saymak için de kullanılır. Belirli değerlere ihtiyacınız yoksa veya değerler kullanılmıyorsa, değerleri alt çizgiye atamanız yeterlidir.

    Paketi açarken bir değeri yoksay

    x, _, y = (1, 2, 3)
    
    >>> x
    1
    
    >>> y 
    3

    Dizini yoksay

    for _ in range(10):     
        do_something()

2
Uluslararasılaştırma işlevi için üçüncü bir kullanım var _("Hello world!").
Jeff Younker

3
İşlemci düzeyinde, aslında "aralıktaki _ için" ile "aralıktaki x için" arasında ve x kullanmamak arasında fark var mıdır? Yoksa sadece insanların okunabilirliği için mi?
iammax

1
@iammax Bulduğum dismodülü kullanarak bayt kodunda bir fark yoktu. Bununla birlikte, insan tarafından okunabilirliğin faydaları açıktır.
Alistair Carscadden

21

Python'da alt çizgi kullanmak için 5 durum vardır.

  1. Son ifadenin değerini yorumlayıcıda saklamak için.

  2. Belirli değerleri göz ardı etmek için. ("Umurumda değil")

  3. Değişkenlerin veya fonksiyonların isimlerine özel anlamlar ve işlevler vermek.

  4. 'Uluslararasılaştırma (i18n)' veya 'Yerelleştirme (l10n)' işlevleri olarak kullanmak için.

  5. Sayı değişmez değerinin basamaklarını ayırmak için.

İşte mingrammer'ın örneklerini içeren güzel bir makale .



3

Python dilleri ile ilgili olarak, _özel bir anlamı yoktur. Bu geçerli bir tanımlayıcı gibi _foo, foo_ya da _f_o_o_.

Herhangi bir özel anlamı _tamamen sözleşmedir. Birkaç vaka yaygındır:

  • Bir değişkenin kullanılması amaçlanmadığında sahte bir ad, ancak sözdizimi / anlambilim için bir ad gereklidir.

    # iteration disregarding content
    sum(1 for _ in some_iterable)
    # unpacking disregarding specific elements
    head, *_ = values
    # function disregarding its argument
    def callback(_): return True
  • Birçok REPL / kabuk, son üst düzey ifadenin sonucunu saklar builtins._.

    Özel tanımlayıcı _, son değerlendirmenin sonucunu saklamak için etkileşimli yorumlayıcıda kullanılır; builtinsmodülde saklanır . Etkileşimli modda değilken, _özel bir anlamı yoktur ve tanımlanmamıştır. [ kaynak ]

    Adların aranma şekli nedeniyle _, çıplak veya genel bir tanımla gölgelenmedikçe , çıplak _anlamına gelir builtins._.

    >>> 42
    42
    >>> f'the last answer is {_}'
    'the last answer is 42'
    >>> _
    'the last answer is 42'
    >>> _ = 4  # shadow ``builtins._`` with global ``_``
    >>> 23
    23
    >>> _
    4

    Not: Bazı kabuklar böyle ipythonatamak yok builtins._ama özel durum _.

  • Uluslararasılaşma ve yerelleştirme bağlamında _, birincil çeviri işlevi için bir takma ad olarak kullanılır.

    gettext.gettext (mesaj)

    Geçerli global etki alanı, dil ve yerel ayar dizinine dayalı olarak iletinin yerelleştirilmiş çevirisini döndürür. Bu işlev yerel ad alanında genellikle _ () olarak adlandırılır (aşağıdaki örneklere bakın).

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.