Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/xml/14.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 如何从xml或tcx文件中获取数据系列_Python_Xml_Parsing_Xpath_Beautifulsoup - Fatal编程技术网

Python 如何从xml或tcx文件中获取数据系列

Python 如何从xml或tcx文件中获取数据系列,python,xml,parsing,xpath,beautifulsoup,Python,Xml,Parsing,Xpath,Beautifulsoup,我想用Python在特定标记之间处理.tcx文件(xml格式)中的数据。 文件格式如下所示 <Track> <Trackpoint> <Time>2015-08-29T22:04:39.000Z</Time> <Position> <LatitudeDegrees>37.198049426078796</LatitudeDegrees>

我想用Python在特定标记之间处理.tcx文件(xml格式)中的数据。
文件格式如下所示

 <Track>
      <Trackpoint>
        <Time>2015-08-29T22:04:39.000Z</Time>
        <Position>
          <LatitudeDegrees>37.198049426078796</LatitudeDegrees>
          <LongitudeDegrees>127.07204628735781</LongitudeDegrees>
        </Position>
        <AltitudeMeters>34.79999923706055</AltitudeMeters>
        <DistanceMeters>7.309999942779541</DistanceMeters>
        <HeartRateBpm>
          <Value>102</Value>
        </HeartRateBpm>
        <Cadence>76</Cadence>
        <Extensions>
          <TPX xmlns="http://www.garmin.com/xmlschemas/ActivityExtension/v2">
            <Watts>112</Watts>
          </TPX>
        </Extensions>
      </Trackpoint>
....Lots of <Trackpoint> ... </Trackpoint>
</Track>

2015-08-29T22:04:39.000Z
37.198049426078796
127.07204628735781
34.79999923706055
7.309999942779541
102
76
112
……很多。。。
最后,我将用“latitude,aighty,…”列创建数据表。。。瓦茨。
首先,我尝试使用BeautifulSoup、xpath等从标记数据(如Watts…/Watts)生成一个列表。 但我是一个处理这些工具的新手。
如何使用Python在xml文件中的标记之间获取数据?

您可以使用
lxml
模块以及
XPath
lxml
非常适合解析XML/HTML、遍历元素树和返回元素文本/属性。您可以使用
XPath
选择特定元素、元素集或元素属性。使用您的示例数据:

content = '''
<Track>
      <Trackpoint>
        <Time>2015-08-29T22:04:39.000Z</Time>
        <Position>
          <LatitudeDegrees>37.198049426078796</LatitudeDegrees>
          <LongitudeDegrees>127.07204628735781</LongitudeDegrees>
        </Position>
        <AltitudeMeters>34.79999923706055</AltitudeMeters>
        <DistanceMeters>7.309999942779541</DistanceMeters>
        <HeartRateBpm>
          <Value>102</Value>
        </HeartRateBpm>
        <Cadence>76</Cadence>
        <Extensions>
          <TPX xmlns="http://www.garmin.com/xmlschemas/ActivityExtension/v2">
            <Watts>112</Watts>
          </TPX>
        </Extensions>
      </Trackpoint>
....Lots of <Trackpoint> ... </Trackpoint>
</Track>
'''

from lxml import etree

tree = etree.XML(content)
time = tree.xpath('Trackpoint/Time/text()')

print(time)

您甚至可以使用
lxml
module跨各种XPath使用迭代Python列表将XML转换为CSV(以便以后导入到数据帧、电子表格或数据库表中)

请注意,最后一个
Watts
节点是一个特殊的、较长的XPath,因为它转义了特殊的名称空间,
xlmns
未在示例XML中注册

import os, csv
import lxml.etree as ET

# SET DIRECTORY
cd = os.path.dirname(os.path.abspath(__file__))

# LOAD XML FILE
xmlfile = 'trackXML.xml'
dom = ET.parse(os.path.join(cd, xmlfile))

# DEFINING COLUMNS
columns = ['latitude', 'longitude', 'altitude', 'distance', 'watts']

# OPEN CSV FILE
with open(os.path.join(cd,'trackData.csv'), 'w') as m:
    writer = csv.writer(m)    
    writer.writerow(columns)

    nodexpath = dom.xpath('//Trackpoint')

    dataline = []   # FOR ONE-ROW CSV APPENDS
    datalines = []  # FOR FINAL OUTPUT 
    for j in range(1,len(nodexpath)+1):        
        dataline = []

        # LOCATE PATH OF EACH NODE VALUE
        latitudexpath = dom.xpath('//Trackpoint[{0}]/Position/LatitudeDegrees/text()'.format(j))
        dataline.append('') if latitudexpath == [] else dataline.append(latitudexpath[0])

        longitudexpath = dom.xpath('//Trackpoint[{0}]/Position/LongitudeDegrees/text()'.format(j))
        dataline.append('') if longitudexpath == [] else dataline.append(longitudexpath[0])

        altitudexpath = dom.xpath('//Trackpoint[{0}]/AltitudeMeters/text()'.format(j))
        dataline.append('') if altitudexpath == [] else dataline.append(altitudexpath[0])

        distancexpath = dom.xpath('//Trackpoint[{0}]/DistanceMeters/text()'.format(j))
        dataline.append('') if distancexpath == [] else dataline.append(distancexpath[0])

        wattsxpath = dom.xpath("//Trackpoint[{0}]/*[name()='Extensions']/*[name()='TPX']/*[name()='Watts']/text()".format(j))
        dataline.append('') if wattsxpath == [] else dataline.append(wattsxpath[0])

        datalines.append(dataline)
        writer.writerow(dataline)

print(datalines)
除CSV文件外,以下是选定列的数据线列表输出:

[['37.198049426078796', '127.07204628735781', '34.79999923706055', '7.309999942779541', '112']]
Python程序迭代在命令行中指定的TCX文件,并为循环活动的所有度量添加一个power字段。
它使用库来提高速度,因为它处理名称空间。在这个程序的早期版本中,我使用了xml.etree.ElementTree,但在名称空间方面遇到了问题。

感谢您提供了简单的解决方案。我得到了除了瓦特以外的其他数据。也许TPX“xmlns=…”标记会导致问题。你能测试一下吗?你的解决方案就是我想要的!但它不起作用。错误消息如下所示。文件“xml2obj.py”,第15行,在中打开(os.path.join(cd,'trackData.csv'),'w',newline='')作为m:TypeError:'newline'是此函数的无效关键字参数这是Python 3解决方案。您可能正在使用Python 2.7,它不将
newline
作为
open()
函数中的参数。只需将其移除即可。请参阅我的编辑。
[['37.198049426078796', '127.07204628735781', '34.79999923706055', '7.309999942779541', '112']]