我正在尝试将RSS 2.0 Feed中的标题标记解析为该Feed中每个条目的三个不同变量。使用ElementTree我已经解析了RSS,这样我就可以使用下面的代码打印每个标题[减去尾随的] ]:

feed = getfeed("http://www.tourfilter.com/dallas/rss/by_concert_date")

for item in feed:  
 print repr(item.title[0:-1])

我包括那个因为,正如你所看到的,item.title是一个repr()数据类型,我不太了解。

交互式窗口中的特定 repr(item.title [0:-1]) print ed如下所示:

'randy travis (Billy Bobs 3/21'
'Michael Schenker Group (House of Blues Dallas 3/26'

用户选择一个乐队,我希望在将每个 item.title 解析为3个变量后(乐队,场地和日期各一个......或者可能是一个阵列或者我不喜欢)知道...)只选择与所选频段相关的那些。然后他们被发送到谷歌进行地理编码,但这是另一个故事。

我已经看过 regex 的一些例子,我正在阅读它们,但它看起来很复杂。是吗?我想也许这里有人会对如何以智能方式做到这一点有一些见解。我应该使用 re 模块吗?输出当前是 repr() s是否重要?有没有更好的办法?我以为我会使用一个循环(这是我的pseudoPython,只是我写的一些注释):

     list = bandRaw,venue,date,latLong  
     for item in feed:  
      parse item.title for bandRaw, venue, date  
       if bandRaw == str(band)   
        send venue name + ", Dallas, TX" to google for geocoding  
        return lat,long  
      list = list + return character + bandRaw + "," + venue + "," + date + "," + lat + "," + long  
     else  

最后,我需要在.csv(逗号分隔)文件中选择的条目如下所示:

band,venue,date,lat,long  
randy travis,Billy Bobs,3/21,1234.5678,1234.5678  
Michael Schenker Group,House of Blues Dallas,3/26,4321.8765,4321.8765

我希望这不是太多问题。我会自己调查一下,以为我应该在这里发帖以确保它得到了答案。

所以,问题是,我如何最好地将 feed 中的每个 repr(item.title [0:-1])解析为3个单独的值然后我可以连接成一个.csv文件?

有帮助吗?

解决方案

不要让正则表达式吓跑你......这非常值得学习。

鉴于上面的示例,您可以尝试重新添加尾部括号,然后使用此模式:

import re
pat = re.compile('([\w\s]+)\(([\w\s]+)(\d+/\d+)\)')
info = pat.match(s)
print info.groups()

('Michael Schenker Group ', 'House of Blues Dallas ', '3/26')

要获得每个组的个人,只需在 info 对象上调用它们:

print info.group(1) # or info.groups()[0]

print '"%s","%s","%s"' % (info.group(1), info.group(2), info.group(3))
"Michael Schenker Group","House of Blues Dallas","3/26"

在这种情况下,正则表达式的难点在于确保您知道标题中所有已知的可能字符。如果'Michael Schenker Group'部分中存在非alpha字符,则必须调整该部分的正则表达式以允许它们。

上面的模式按如下方式分解,从左到右解析:

([\ w \ s] +):匹配任何单词或空格字符(加号表示应该有一个或多个此类字符)。括号表示匹配将作为一组捕获。这是“Michael Schenker Group”。部分。如果这里可以有数字和破折号,你需要修改方括号之间的部分,它们是集合的可能字符。

\(:一个文字括号。反斜杠会转义括号,因为否则它会被视为正则表达式命令。这是“(”字符串的一部分。

([\ w \ s] +):与上面的相同,但这一次与“House of Blues Dallas”匹配。部分。在括号中,它们将被捕获为第二组。

(\ d + / \ d +):数字3和26与中间的斜杠匹配。在括号中,它们将被捕获为第三组。

\):上面的闭括号。

正则表达式的python介绍非常好,你可能想花一个晚上来讨论它 http://docs.python.org/library/re.html#module-re 。另外,请查看Dive Into Python,其中有一个友好的介绍: http://diveintopython3.ep.io /regular-expressions.html

编辑:请参阅下面的zacherates,他有一些很好的编辑。两个头比一个好!

其他提示

正则表达式是解决此问题的绝佳方法:

>>> import re
>>> s  = 'Michael Schenker Group (House of Blues Dallas 3/26'
>>> re.match(r'(.*) \((.*) (\d+/\d+)', s).groups()
('Michael Schenker Group', 'House of Blues Dallas', '3/26')

作为旁注,您可能需要查看 Universal Feed Parser ,以便将RSS解析作为Feed处理有一个不正常的坏习惯。

修改

关于你的评论......偶尔包含在“s而不是s”中的字符串与你使用repr的事实有关。字符串的repr通常用's分隔,除非该字符串包含一个或多个,而是使用“s”,以便不必转义:

>>> "Hello there"
'Hello there'
>>> "it's not its"
"it's not its"

注意不同的报价样式。

关于 repr(item.title [0:-1])部分,不知道你从哪里得到它但我很确定你可以简单地使用 item.title 。你所要做的就是从字符串中删除最后一个字符,然后在其上调用 repr(),它什么都不做。

您的代码应如下所示:

import geocoders # from GeoPy
us = geocoders.GeocoderDotUS()

import feedparser # from www.feedparser.org
feedurl = "http://www.tourfilter.com/dallas/rss/by_concert_date"
feed = feedparser.parse(feedurl)

lines = []
for entry in feed.entries:
    m = re.search(r'(.*) \((.*) (\d+/\d+)\)', entry.title)  
    if m:
        bandRaw, venue, date = m.groups()

        if band == bandRaw:
            place, (lat, lng) = us.geocode(venue + ", Dallas, TX")
            lines.append(",".join([band, venue, date, lat, lng]))

result = "\n".join(lines)

编辑:将 list 替换为 lines 作为var名称。 list 是内置函数,不应用作变量名。遗憾。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top