Как объединить элементы с одинаковым тегом в одном и том же родительском элементе в Python XML несмотря на их атрибуты? - PullRequest
2 голосов
/ 10 апреля 2020

У меня есть XML, структурированная так:

    <?xml version="1.0" encoding="utf-8" ?>
    <pages>
    <page id="1" bbox="0.000,0.000,462.047,680.315" rotate="0">
    <textbox id="0" bbox="179.739,592.028,261.007,604.510">
    <textline bbox="179.739,592.028,261.007,604.510">
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">C</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">A</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">P</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">I</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">T</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">O</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">L</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">O</text>
    <text> </text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">I</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">I</text>
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">I</text>
    <text>
    </text>
    </textline>
    </textbox>
</page>
</pages>

Я хочу объединить все теги text с одинаковым размером текста внутри одного родителя (текстовой строки), чтобы отдельные буквы были присоединился. Теги страниц, страницы и текстовые поля будут сохранены. Я хотел бы сохранить порядок, в котором представлены буквы, например:

<?xml version="1.0" encoding="utf-8" ?>
    <pages>
    <page id="1" bbox="0.000,0.000,462.047,680.315" rotate="0">
    <textbox id="0" bbox="179.739,592.028,261.007,604.510">
    <textline bbox="179.739,592.028,261.007,604.510">
    <text font="NUMPTY+ImprintMTnum"  ncolour="0" size="12.482">CAPITOLO III</text>
    </textline>
    </textbox>
</page>
</pages>

Я попытался посмотреть на inte rnet, но мои попытки не сработали. Вот что я попробовал:

import xml.etree.ElementTree as ET
MY_XML = ET.parse('fe.xml')
group_list = MY_XML.findall("./pages/page/textbox/textline") # I do this because the actual xml is bigger with several groups
text_list = []
for group in group_list:
    string_text = ""
    for child in group :
        for super_child in child:
            if(super_child.text is not None): #Just in case None value because I cannot use string addition
                string_text = string_text + super_child.text + " "
    text_list.append(string_text)
    #I stored all the info in 1 group as a value in this list because like I stated my overall xml might be bigger with more than 1 group
for group in group_list:
    for elem in group.findall("./pages/page/textbox/textline/text"):
        #loop over all possible <group> and removes all <group_info> inside
        group.remove(elem)

#And finally to append the information gathered:
for group in group_list:
    Text_elem = ET.Element("text")
    Text_elem.text = text_list[group_list.index(group)]
    group.append(Text_elem)
print(group_list)

Я не знаю, как заставить это работать, пожалуйста, помогите.

1 Ответ

0 голосов
/ 10 апреля 2020

Одна проблема в вашем коде состоит в том, что MY_XML.findall("./pages/page/textbox/textline") возвращает пустой список. Элементом root является pages, который является контекстом для findall(). Так что findall("./page/textbox/textline") будет работать.

Вот программа, которая производит желаемый вывод:

import xml.etree.ElementTree as ET

MY_XML = ET.parse('fe.xml')

textlines = MY_XML.findall("./page/textbox/textline")

for textline in textlines:
    fulltext = []
    for text_elem in list(textline):
        # Get the text of each 'text' element and then remove it
        fulltext.append(text_elem.text)
        textline.remove(text_elem)

    # Create a new 'text' element and add the joined letters to it
    new_text_elem = ET.Element("text", font="NUMPTY+ImprintMTnum", ncolour="0", size="12.482")
    new_text_elem.text = "".join(fulltext).strip()

    # Append the new 'text' element to its parent
    textline.append(new_text_elem)

print(ET.tostring(MY_XML.getroot(), encoding="unicode"))

Вывод:

<pages>
  <page id="1" bbox="0.000,0.000,462.047,680.315" rotate="0">
    <textbox id="0" bbox="179.739,592.028,261.007,604.510">
      <textline bbox="179.739,592.028,261.007,604.510">
    <text font="NUMPTY+ImprintMTnum" ncolour="0" size="12.482">CAPITOLO III</text></textline>
    </textbox>
  </page>
</pages>
...