Python'da iddiaları nasıl devre dışı bırakırım?
Yani, bir iddia başarısız olursa, onun bir atmasını AssertionErrordeğil, devam etmesini istemiyorum .
Bunu nasıl yaparım?
Yanıtlar:
Python'da iddiaları nasıl devre dışı bırakırım?
Tek bir işlemi, ortamı veya tek bir kod satırını etkileyen birden çok yaklaşım vardır.
Her birini gösteriyorum.
Kullanılması -Obayrağı (sermaye O) bir işlemdeki tüm assert ifadeleri devre dışı bırakır.
Örneğin:
$ python -Oc "assert False"
$ python -c "assert False"
Traceback (most recent call last):
File "<string>", line 1, in <module>
AssertionError
Devre dışı bırakmakla, onu takip eden ifadeyi de çalıştırmadığını kastettiğime dikkat edin:
$ python -Oc "assert 1/0"
$ python -c "assert 1/0"
Traceback (most recent call last):
File "<string>", line 1, in <module>
ZeroDivisionError: integer division or modulo by zero
Bu bayrağı ayarlamak için bir ortam değişkeni de kullanabilirsiniz.
Bu, ortamı kullanan veya miras alan her süreci etkileyecektir.
Örneğin, Windows'ta ortam değişkenini ayarlama ve ardından temizleme:
C:\>python -c "assert False"
Traceback (most recent call last):
File "<string>", line 1, in <module>
AssertionError
C:\>SET PYTHONOPTIMIZE=TRUE
C:\>python -c "assert False"
C:\>SET PYTHONOPTIMIZE=
C:\>python -c "assert False"
Traceback (most recent call last):
File "<string>", line 1, in <module>
AssertionError
Unix'te aynı ( ilgili işlevsellik için set ve unset kullanarak )
Sorunuza devam edin:
bir iddia başarısız olursa, bir AssertionError atmasını değil, devam etmesini istiyorum.
Başarısız olan kodun kullanılmasını istiyorsanız, kontrol akışının onaylamaya ulaşmamasını sağlayabilirsiniz, örneğin:
if False:
assert False, "we know this fails, but we don't get here"
veya onaylama hatasını yakalayabilirsiniz:
try:
assert False, "this code runs, fails, and the exception is caught"
except AssertionError as e:
print(repr(e))
hangi yazdırır:
AssertionError('this code runs, fails, and the exception is caught')
ve ele aldığınız noktadan devam edeceksiniz AssertionError.
Bunun gibi bir iddia ifadesi:
assert expression #, optional_message
Eşdeğerdir
if __debug__:
if not expression: raise AssertionError #(optional_message)
Ve,
yerleşik değişken
__debug__, optimizasyon istendiğindeTruenormal koşullar altındadırFalse(komut satırı seçeneği-O).
ve Ötesi
'A atamalar
__debug__yasa dışıdır. Yerleşik değişkenin değeri, yorumlayıcı başladığında belirlenir.
Kullanım belgelerinden:
Temel optimizasyonları açın. Bu, derlenmiş (bayt kodu) dosyalar için dosya adı uzantısını .pyc'den .pyo'ya değiştirir. Ayrıca bkz. PYTHONOPTIMIZE.
ve
Bu boş olmayan bir dizeye ayarlanırsa,
-Oseçeneği belirtmeye eşdeğerdir . Bir tam sayıya ayarlanırsa,-Obirden çok kez belirtmeye eşdeğerdir .
if False: assert False) Veya Onaylama hatasını yakalayabilirsiniz. Seçimleriniz bunlar. Sorunuzu yanıtlamak için yanıtı güncelledi.
foo()kapalı ve anahtarlama iddialar: with skip_assertion(): foo(). Bunun yararı, işleve başka bir bayrak eklemem
Assertnesneleri Passnesnelerle değiştirin ). Bir bağlam yöneticisi bunun için doğrudan çalışmaz, ancak bu şekilde dekore edilmiş işlevleri kullanan bir tür mekanizmaya sahip olabilirsiniz. Ne olursa olsun, tavsiye etmiyorum. Bunu yapmak istemenizin nedeninin kontrol etmediğiniz kodu aramanız ve AssertionErrors'ı almanız olduğundan şüpheleniyorum. Öyleyse muhtemelen farklı bir düzeltme bulmanız gerekir.
Python'u -O bayrağıyla çağırın:
test.py:
assert(False)
print 'Done'
Çıktı:
C:\temp\py>C:\Python26\python.exe test.py
Traceback (most recent call last):
File "test.py", line 1, in <module>
assert(False)
AssertionError
C:\temp\py>C:\Python26\python.exe -O test.py
Done
Zaten verilen iki cevap Hem (biriyle Python çağrı geçerlidir -Oveya -OOkomut satırında).
İşte aralarındaki fark:
-OTemel optimizasyonları açın. Bu, derlenmiş (bayt kodu) dosyalar için dosya adı uzantısını .pyc'den .pyo'ya değiştirir.
-OOOptimizasyonlara ek olarak dokümanları atın -O.
Kullanım python -O:
$ python -O
>>> assert False
>>>
You should DEĞİL devre dışı (çoğu) iddialar. Dikkat başka yerde olduğunda, beklenmedik hataları yakalarlar. "On'un gücü" ndeki Kural 5'e bakın .
Bunun yerine, aşağıdaki gibi bazı pahalı iddia kontrollerini koruyun:
import logging
logger = logging.getLogger(__name__)
if logger.getEffectiveLevel() < logging.DEBUG:
ok = check_expensive_property()
assert ok, 'Run !'
Önemli iddiaları tutmanın ve assertifadelerin optimize edilmesine izin vermenin bir yolu, onları bir seçim ifadesi içinde yükseltmektir:
if foo_is_broken():
raise AssertionError('Foo is broken!')
__debug__ama buna izin verilmiyor.