Как да получите всички поделементи на дърво на елементи с Python ElementTree?

Искам да намеря начин да получа всички поделементи на дърво на елементи като начина, по който го прави ElementTree.getchildren(), тъй като getchildren() е остарял след Python версия 2.7.
Не искам да го използвам повече, въпреки че все още мога използвайте го в момента.


person j5shi    schedule 02.05.2012    source източник


Отговори (5)


Всички поделементи (потомци) на elem:

all_descendants = list(elem.iter())

По-пълен пример:

>>> import xml.etree.ElementTree as ET
>>> a = ET.Element('a')
>>> b = ET.SubElement(a, 'b')
>>> c = ET.SubElement(a, 'c')
>>> d = ET.SubElement(a, 'd')
>>> e = ET.SubElement(b, 'e')
>>> f = ET.SubElement(d, 'f')
>>> g = ET.SubElement(d, 'g')
>>> [elem.tag for elem in a.iter()]
['a', 'b', 'e', 'c', 'd', 'f', 'g']

За да изключите самия корен:

>>> [elem.tag for elem in a.iter() if elem is not a]
['b', 'e', 'c', 'd', 'f', 'g']
person Eli Bendersky    schedule 02.05.2012
comment
Съжалявам, Ели, но може би не съм се разбрал, просто искам да получа всички поделементи, не и корена. т.е. коренът е нежелан тук. но мисля, че вашият метод също съдържа основния обект, нали? - person j5shi; 02.05.2012
comment
Но какво ще стане, ако има повече от една структура с етикет „a“, вложена в елемент „a“ и искам да получа всички поделементи на всички структури „a“? - person j5shi; 02.05.2012
comment
Елементните обекти могат да се повтарят и без използване на iter(). Елементът се държи също като списък; така че можете също да индексирате поделементите. - person pepr; 02.05.2012
comment
@pepr: да, но това ви дава само непосредствените потомци на елемента, а не всички потомци - person Eli Bendersky; 02.05.2012
comment
@Eli Bendersky: Разбирам. Но getchildren() също връща само непосредствените деца. Старият еквивалент на новото list(elem.iter()) е list(elem.getiterator()). Зависи какво наистина иска Стивън. - person pepr; 02.05.2012

в pydoc се споменава да се използва метод list() над възела, за да се получат дъщерни елементи.
list(elem)

person Harshal Zope    schedule 22.08.2018
comment
list() вече е предложен в предишни отговори, а също и в отговор, маркиран като правилен. Нямаше реална нужда от този отговор. - person Goran Kutlaca; 22.08.2018
comment
@GoranKutlaca: проверете отговора ми. той гласи да се използва list(elem) да не се използва list(elem.iter()). Има разлика и в двете повиквания. list(elem) ще даде само поделементи. - person Harshal Zope; 27.08.2018
comment
Това е, което търсех... въпросът за съжаление е малко двусмислен, въпреки че препратката към деца, а не всички потомци, предполага, че това е, което OP също искаше. - person mike rodent; 16.04.2021

Ако искате да получите всички елементи 'a', можете да използвате:

a_lst = list(elem.iter('a'))

Ако elem също е 'a', то ще бъде включено.

person pepr    schedule 02.05.2012

Може би това не отговаря на действителния въпрос на OP, но в по-голям смисъл бих предложил, ако някой иска да получи всички елементи, наименувани с определено име, напр. 'object' може да използва (алтернативен подход към @Turtles Are Cute, който поне за мен изглежда по-естествен):

objs = tree.findall('object')

което също връща списък.

person Eypros    schedule 24.08.2018

Нито един от съществуващите отговори няма да намери всички деца. Това решение използва BeautifulSoup вместо ETree, но ще намери всички деца, вместо само най-високо ниво:

from bs4 import BeautifulSoup    

with open(filename) as f:
    soup = BeautifulSoup(f, 'xml')

results = soup.find_all('element_name')
person Turtles Are Cute    schedule 02.03.2017