python查询维基百科的表现

时间:2013-01-10 14:03:34

标签: python wikipedia

我需要查询维基百科只是为了一个非常特殊的目的,即获取给定网址的文本。更准确一点:

我有大约14.000个英文语料库的维基百科网址,我需要获取文本,或至少引入每个网址。我的进一步处理将在python中,因此这将是首选语言。

我正在寻找性能最佳的方法,并制定了4种不同的方法:

  1. 获取xml转储并通过python直接解析 - >这里的另一个问题是:如何查询xml文件,知道网址?
  2. 获取xml,设置数据库并使用python
    查询sql - >进一步的问题是:如何查询sql,知道网址?
  3. 使用维基百科api并直接通过python
  4. 查询
  5. 只是抓取这些维基百科页面(这可能是一种偷偷摸摸的,也很烦人,因为它的HTML和没有纯文本)
  6. 我应该使用哪种方法,i。即哪种方法具有最佳性能并且以某种方式标准化?

2 个答案:

答案 0 :(得分:8)

一些想法:

  

我有大约14.000个英文语料库的维基百科网址,我需要获取文本,或至少引入每个网址。

     

1 - 获取xml转储并直接通过python

解析

英语维基百科目前有4,140,​​640篇文章。您对14,000篇文章感兴趣,或者约占总数的百分之三十。这听起来太稀疏了,不允许倾倒所有文章是最好的方法。

  

2 - 获取xml,设置数据库并使用python

查询sql

您是否期望您感兴趣的一组文章能够增长或改变?如果您需要快速响应文章集中的更改,则本地数据库可能很有用。但你必须保持最新。如果速度足够快,使用API​​获取实时数据会更简单。

  

4 - 只是抓取这些维基百科页面(这可能有点偷偷摸摸,也很烦人,因为它的HTML和没有纯文本)

如果你可以从API中得到你需要的东西,那将比抓取维基百科网站更好。

  

3 - 使用维基百科api并通过python直接查询

根据您感兴趣的文章百分比较低,为0.338%,这可能是最好的方法。

请务必查看The MediaWiki API documentationAPI Reference。还有python-wikitools module

  

我需要获取文本,或至少是介绍

如果你真的只需要介绍,这将节省大量的流量,并且真正使得使用API​​成为目前为止的最佳选择。

有多种方法可以检索介绍,这是一个好方法:

http://en.wikipedia.org/w/api.php?action=query&prop=extracts&exintro&format=xml&titles=Python_(programming_language)

如果您一次要处理的请求很多,可以将它们分组为最多20篇文章:

http://en.wikipedia.org/w/api.php?action=query&prop=extracts&exintro&exlimit=20&format=xml&titles=Python_(programming_language)|History_of_Python|Guido_van_Rossum

通过这种方式,您可以在700次往返中检索您的14,000篇文章介绍。

注意: The API reference exlimit文档说明:

  

不超过20个(机器人20个)允许

另请注意: The API documentation section on Etiquette and usage limits说:

  

如果您按顺序而不是并行地提出请求(即等待一个请求在发送新请求之前完成,这样您就不会同时发出多个请求),那么您肯定应该没事的。还可以尝试将内容组合到一个请求中(例如,在titles参数中使用多个标题,而不是为每个标题发出新请求。

维基百科不断更新。如果您需要刷新数据,则可以跟踪修订ID和时间戳,以便识别哪些本地文章已过时。您可以使用(例如):

检索修订信息(以及介绍,此处包含多篇文章)

http://en.wikipedia.org/w/api.php?action=query&prop=revisions|extracts&exintro&exlimit=20&rvprop=ids|timestamp&format=xml&titles=Python_(programming_language)|History_of_Python|Guido_van_Rossum

答案 1 :(得分:0)

这也只是答案的一部分,我在jimhark提出的一个可能的解决方案上做了一些描述:

维基百科api

我使用了这段代码,保存在query.py

import urllib2
import xml.etree.ElementTree as ET
import numpy as np

for i in np.arange(0,1000):
    url = 'http://en.wikipedia.org/w/api.php?format=xml&action=query&titles=Fish&prop=revisions&rvprop=content'
    response = urllib2.urlopen(url)
    html_string = response.read()
    a = ET.fromstring(html_string)
    try :
        a.find('query').find('pages').find('page').find('revisions').find('rev').text
    except (AttributeError):
        pass

并运行python -m cProfile query.py

这不是非常智能的分析,因为很可能Wikipeda api会将查询缓存到fish的页面。

结果:

1431056 function calls (1412734 primitive calls) in 686.813 seconds

几乎所有事情都因为:

ncalls  tottime  percall  cumtime  percall filename:lineno(function)
118081  644.566    0.005  644.566    0.005 {method 'recv' of '_socket.socket' objects}

我会尝试将此用于我的数据集并告知您。