-2

我在 Python 中使用 urllib2 和 sre 来解析来自 aprs.fi 的数据,因此我可以在我正在处理的一些实时高海拔气球代码中使用天气数据。解析代码非常简单:

import urllib2
import sre

APRStracking = urllib2.urlopen( "http://api.aprs.fi/api/get?name=KD8REX&what=loc&apikey=42457.M4AFa3hdkXG31&format=xml" )

APRSxml = APRStracking.read()

latitude = sre.findall( '<la.*>(.*)</la.*>', APRSxml )
print latitude

我试图解析的数据是一个 XML,它看起来像:

<xml>
   <command>get</command>
   <result>ok</result>
   <what>loc</what>
   <found>1</found>
   <entries>
      <entry>
         <name>KD8REX</name>
         <type>l</type>
         <time>1339339410</time>
         <lasttime>1339339410</lasttime>
         <lat>41.95550</lat>
         <lng>-83.65567</lng>
         <altitude>2204.62</altitude>
         <course>15</course>
         <speed>15</speed>
         <symbol>/O</symbol>
         <srccall>KD8REX</srccall>
         <dstcall>APT311</dstcall>
         <status>UofM H.A.S. - Go Blue!</status>
         <status_lasttime>1339339600</status_lasttime>
         <path>WIDE1-1,WIDE3-3,qAR,W8SGZ</path>
      </entry>
   </entries>
</xml>

我对 Python 不是很熟悉,但我对 ser.findall() 的理解是,它通过 APRSxml 查找与正则表达式匹配的任何字符串,然后将括号之间的内容附加到列表“纬度”中。所以,在这个例子中,匹配正则表达式的两个值是“lasttime”和“lat”。但是,当我运行此代码时,它只输出<lat>值,而不是<lasttime>. 坦率地说,这就是我真正需要的代码才能工作,但出于好奇,如果有人能告诉我为什么它没有按预期运行,我将不胜感激。谢谢。

4

4 回答 4

4

查看form参数,我注意到您可以指定form=xml. 我将其更改为json并查看,您得到了 JSON!

{
  "command":"get",
  "result":"ok",
  "what":"loc",
  "found":1,
  "entries":[
    {
      "name":"KD8REX",
      "type":"l",
      "time":"1339339410",
      "lasttime":"1339339410",
      "lat":"41.95550",
      "lng":"-83.65567",
      "altitude":"2204.62",
      "course":"15",
      "speed":"15",
      "symbol":"\/O",
      "srccall":"KD8REX",
      "dstcall":"APT311",
      "status":"UofM H.A.S. - Go Blue!",
      "status_lasttime":"1339339600",
      "path":"WIDE1-1,WIDE3-3,qAR,W8SGZ"
    }
  ]
}

很容易解析。比 XML 更简单:

import urllib2, json

url = 'http://api.aprs.fi/api/get?name=KD8REX&what=loc&apikey=42457.M4AFa3hdkXG31&format=json'
data = json.loads(urllib2.urlopen(url).read())

for entry in data['entries']:
  print 'Latitude:', entry['lat']

这真的很容易使用。data只是一个 Python 字典。

于 2012-06-26T04:18:41.743 回答
0

Python 包含一个易于使用的 XML 解析器,非常适合此任务:

>>> import urllib2
>>> from xml.etree.ElementTree import parse
>>> APRStracking = urllib2.urlopen("http://api.aprs.fi/api/get?name=KD8REX&what=loc&apikey=42457.M4AFa3hdkXG31&format=xml")
>>> tree = parse(APRStracking)
>>> tree.find('entries/entry/lat').text
'41.95550'
于 2012-06-26T05:27:45.240 回答
0

您需要将贪婪的星星更改为惰性匹配(*?)。

>>> re.findall('<la.*?>(.*?)</la.*?>', APRSxml )
['1339339410', '41.95550']

当前发生的是<la.*>匹配从第一次la到最后一次出现的所有内容>,仍然允许表达式的其余部分找到匹配项。所以,<la.*>匹配

<lasttime>1339339410</lasttime><lat>

解释为什么不报告 lasttime 值。

于 2012-06-26T04:07:52.890 回答
0

试试这个非贪婪版本:

latitude = re.findall('<la.*?>(.*?)</la.*?', APRSxml)
>>> print latitude
['1339339410', '41.95550']

但是,如果您想要“纬度”,为什么不这样做呢?

latitude = re.findall('<lat>(.*?)<', APRSxml)
于 2012-06-26T04:08:17.303 回答