синтаксический анализ python 3.x xml похож на plistlib? - PullRequest
0 голосов
/ 18 января 2012

У меня есть данные GPS, хранящиеся в виде файла .tcx. Это XML-файл (начало файла ниже)

<?xml version="1.0" encoding="utf-8"?>
<TrainingCenterDatabase xmlns="http://www.garmin.com/xmlschemas/TrainingCenterDatabase/v2" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:tp1="http://www.garmin.com/xmlschemas/TrackPointExtension/v1" xmlns:gpx="http://www.topografix.com/GPX/1/1" xsi:schemaLocation="http://www.garmin.com/xmlschemas/TrainingCenterDatabase/v2 http://www.garmin.com/xmlschemas/TrainingCenterDatabasev2.xsd">
    <Activities>
        <Activity Sport="Other">
            <Id>2012-01-17T11:44:35Z</Id>
            <Lap StartTime="2012-01-17T11:44:35Z">
                <TotalTimeSeconds>0</TotalTimeSeconds>
                <DistanceMeters>0</DistanceMeters>
                <Calories>0</Calories>
                <Intensity>Active</Intensity>
                <TriggerMethod>Manual</TriggerMethod>
                <Track>
                    <Trackpoint>
                        <Time>2012-01-17T11:44:35Z</Time>
                        <Position>
                            <LatitudeDegrees>59.720211518183351</LatitudeDegrees>

Единственной схожей вещью, с которой я работал, были списки Apple .plists, которые используют похожий формат, хотя информация, как я полагаю, вложена в тег <dictionary>.

Где следующее даст мне вложенные словари ...

import plistlib
pl = plistlib.readPlist('/Users/name/Documents/file.plist')

for sub_dict in pl:
    print(sub_dict['keyA'])
    print(sub_dict['keyD'])
    print(sub_dict['keyE'])
    print(sub_dict['keyG'])

Мне известны xml.dom.minidom, etree и lxml, но у меня возникли проблемы с определением того, как получить тот же вывод, который дает мне вышеуказанный модуль plistlib.

Моя конечная цель - объединить выбранные ключи из двух наборов данных. Один шаг за раз ...

РЕДАКТИРОВАТЬ -----------------

У меня что-то работает:

from xml.dom.minidom import parse
doc = parse('/Users/name/Documents/GPS/gps.tcx')
lat = doc.getElementsByTagName("LatitudeDegrees")
time = doc.getElementsByTagName("Time")

for x in lat:
    print(x.firstChild.data)

1 Ответ

1 голос
/ 19 января 2012

Мне пришлось добавить закрывающие теги в ваш опубликованный XML, чтобы анализатор lxml мог его проанализировать.Как только это будет сделано, данные Time и LatitudeDegrees могут быть извлечены с использованием вызовов doc.xpath.

import lxml.etree as ET
import io

content='''<?xml version="1.0" encoding="utf-8"?>
<TrainingCenterDatabase xmlns="http://www.garmin.com/xmlschemas/TrainingCenterDatabase/v2" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:tp1="http://www.garmin.com/xmlschemas/TrackPointExtension/v1" xmlns:gpx="http://www.topografix.com/GPX/1/1" xsi:schemaLocation="http://www.garmin.com/xmlschemas/TrainingCenterDatabase/v2 http://www.garmin.com/xmlschemas/TrainingCenterDatabasev2.xsd">
    <Activities>
        <Activity Sport="Other">
            <Id>2012-01-17T11:44:35Z</Id>
            <Lap StartTime="2012-01-17T11:44:35Z">
                <TotalTimeSeconds>0</TotalTimeSeconds>
                <DistanceMeters>0</DistanceMeters>
                <Calories>0</Calories>
                <Intensity>Active</Intensity>
                <TriggerMethod>Manual</TriggerMethod>
                <Track>
                    <Trackpoint>
                        <Time>2012-01-17T11:44:35Z</Time>
                        <Position>
                            <LatitudeDegrees>59.920211518183351</LatitudeDegrees>
</Position>
</Trackpoint>
</Track>
</Lap>
</Activity>
</Activities>
</TrainingCenterDatabase>
'''

doc = ET.fromstring(content)

ns = {'ns':'http://www.garmin.com/xmlschemas/TrainingCenterDatabase/v2'}
for trackpoint in doc.xpath('//ns:Trackpoint', namespaces = ns):
    print(trackpoint.xpath('(ns:Time|ns:Position/ns:LatitudeDegrees)/text()', namespaces = ns))

урожайность

['2012-01-17T11:44:35Z', '59.920211518183351']
...