Jak sprawdzić, czy obiekt ma atrybut w Pythonie
Czy istnieje sposób w Pythonie, aby określić, czy obiekt ma jakiś atrybut? Na przykład:
>>> a = SomeClass()
>>> a.someProperty = value
>>> a.property
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: SomeClass instance has no attribute 'property'
Jak możesz sprawdzić, czy a
ma atrybut property
przed użyciem?
9 answers
Spróbuj hasattr()
:
if hasattr(a, 'property'):
a.property
EDIT: Zobacz odpowiedź zweiterlinde poniżej, który oferuje dobrą radę o proszeniu o przebaczenie! Bardzo pythoniczne podejście!
Ogólna praktyka w Pythonie polega na tym, że jeśli właściwość prawdopodobnie będzie tam przez większość czasu, po prostu wywołaj ją i albo pozwól, aby wyjątek rozprzestrzeniał się, albo pułapkuj ją blokiem try / except. Będzie to prawdopodobnie szybsze niż hasattr
. Jeśli nieruchomość prawdopodobnie nie będzie tam przez większość czasu, lub nie jesteś pewien, za pomocą hasattr
będzie prawdopodobnie szybsze niż wielokrotne wpadanie w blok WYJĄTKÓW.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-03-21 19:26:12
Jak odpowiedział Jarret Hardie, to da radę. Chciałbym jednak dodać, że wielu w społeczności Pythona zaleca strategię "łatwiej prosić o przebaczenie niż pozwolenie" (EAFP), a nie "spójrz, zanim skoczysz" (LBYL). Zobacz te referencje:
EAFP vs LBYL (był Re: na razie trochę rozczarowany)
EAFP vs. Lbyl @Code Like A Pythonist: Idiomatic Python
Ie:
try:
doStuff(a.property)
except AttributeError:
otherStuff()
... jest preferowany do:
if hasattr(a, 'property'):
doStuff(a.property)
else:
otherStuff()
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-05-27 09:30:53
Możesz użyć hasattr()
lub catch AttributeError
, ale jeśli naprawdę chcesz, aby wartość atrybutu była domyślna, jeśli jej nie ma, najlepszą opcją jest użycie getattr()
:
getattr(a, 'property', 'default value')
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2013-09-24 20:22:25
Myślę, że to, czego szukasz, to hasattr . Jednak polecam coś takiego, jeśli chcesz wykryć właściwości Pythona-
try:
getattr(someObject, 'someProperty')
except AttributeError:
print "Doesn't exist"
else
print "Exists"
Wadą jest to, że błędy atrybutów w kodzie właściwości __get__
są również przechwytywane.
W Przeciwnym Razie do-
if hasattr(someObject, 'someProp'):
#Access someProp/ set someProp
pass
Docs: http://docs.python.org/library/functions.html
Warning:
Powodem mojej rekomendacji jest to, że hasattr nie wykrywa właściwości.
Link: http://mail.python.org/pipermail/python-dev/2005-December/058498.html
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-03-04 15:29:11
Według pydoc, hasattr(obj, prop) po prostu wywołuje getattr (obj, prop) i wychwytuje wyjątki. Tak samo ważne jest owinięcie atrybutu access instrukcją try i przechwycenie AttributeError, jak wcześniejsze użycie metody hasattr ().
a = SomeClass()
try:
return a.fake_prop
except AttributeError:
return default_value
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2009-03-04 14:56:26
Chciałbym zasugerować unikanie tego:
try:
doStuff(a.property)
except AttributeError:
otherStuff()
Użytkownik @ jpalecek wspomniał o tym: Jeśli AttributeError
występuje wewnątrz doStuff()
, jesteś zagubiony.
Może to podejście jest lepsze:
try:
val = a.property
except AttributeError:
otherStuff()
else:
doStuff(val)
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2016-08-26 13:04:30
W zależności od sytuacji możesz sprawdzić za pomocą isinstance
jaki masz obiekt, a następnie użyć odpowiednich atrybutów. Wraz z wprowadzeniem abstrakcyjnych klas bazowych w Pythonie 2.6/3.0 podejście to stało się również znacznie potężniejsze (zasadniczo ABC pozwalają na bardziej wyrafinowany sposób pisania kaczek).
Jedna sytuacja, w której jest to użyteczne, byłaby taka, gdyby dwa różne obiekty miały atrybut o tej samej nazwie, ale o innym znaczeniu. Używanie tylko hasattr
może wtedy prowadzić do dziwnych błędów.
Miłym przykładem jest rozróżnienie pomiędzy iteratorami i iterabami (zobacz to pytanie). Metody __iter__
w iteratorze i iterable mają tę samą nazwę, ale są semantycznie zupełnie inne! Więc {[1] } jest bezużyteczny, ale isinstance
RAZEM Z ABC zapewnia czyste rozwiązanie.
Zgadzam się jednak, że w większości sytuacji najodpowiedniejszym rozwiązaniem jest podejście hasattr
(opisane w innych odpowiedziach).
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-23 12:26:34
EDIT: takie podejście ma poważne ograniczenia. Powinno działać, jeśli obiekt jest iterowalny . Proszę sprawdzić komentarze poniżej.
Jeśli używasz Pythona 3.6 lub wyższego jak ja, istnieje wygodna alternatywa, aby sprawdzić, czy obiekt ma określony atrybut:
if 'attr1' in obj1:
print("attr1 = {}".format(obj1["attr1"]))
Nie jestem jednak pewien, które podejście jest teraz najlepsze. używając hasattr()
, używając getattr()
lub używając in
. Komentarze są mile widziane.Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2018-04-26 08:54:31
Mam nadzieję, że spodziewasz się hasattr (), ale staraj się unikać hasattr() i preferuj getattr (). getattr () jest szybsze niż hasattr ()
Korzystanie z hasattr():
if hasattr(a, 'property'):
print a.property
To samo tutaj używam getattr aby uzyskać Właściwość jeśli nie ma właściwości zwraca none
property = getattr(a,"property",None)
if property:
print property
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/doraprojects.net/template/agent.layouts/content.php on line 54
2017-05-22 05:47:18