当前位置:   article > 正文

使用lxml的xpath读取网页中的表格并转化为pandas的DataFrame_urllib request 解析为dataframe

urllib request 解析为dataframe

lxml是Python的一个用来读写HTML和XML格式数据的库,她可以高效而且可靠地解析大文件。lxml有一个编程接口lxml.html可以用来处理HTML。

lxml库内置了对xpath的支持,所以可以很方便地使用xpath来获取html文件中的各个标签的内容。

XPath 是一门在 XML 文档中查找信息的语言。XPath 可用来在 XML 文档中对元素和属性进行遍历。

XPath 是 W3C XSLT 标准的主要元素,并且 XQuery 和 XPointer 都构建于 XPath 表达之上。

因此,对 XPath 的理解是很多高级 XML 应用的基础。

xpath的语法非常简单,可以从w3school学习一下语法,十几分钟就足够了。

好了,开始干活。我们获取这个页面的第一个表格。

from lxml.html import parse

from urllib.request import urlopen

# 使用的是Python3, Python2可能需要from urllib2 import urlopen

doc = parse(urlopen('http://www.w3school.com.cn/xpath/xpath_syntax.asp'))

# 打开url, 并且使用parse方法转化为可以使用xpath查找的格式

tables = doc.xpath('//table')

# 查找文档中所有的table, 返回一个列表
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

我们查看一下网页的源代码,找到需要获取的表格

<table class="dataintable">     

<tr>

<th style="width:25%;">表达式</th>

<th>描述</th>

</tr>

<tr>

<td>nodename</td>

<td>选取此节点的所有子节点。</td>

</tr>

<tr>

<td>/</td>

<td>从根节点选取。</td>

</tr>

<tr>

<td>//</td>

<td>从匹配选择的当前节点选择文档中的节点,而不考虑它们的位置。</td> 

</tr>

<tr>

<td>.</td>

<td>选取当前节点。</td>

</tr>

<tr>

<td>..</td>

<td>选取当前节点的父节点。</td>

</tr>

<tr>

<td>@</td>

<td>选取属性。</td>

</tr>

</table>
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59

表格的第一行为标题,下面的各行为数据,我们定义一个函数来分别得到它们:

def _unpack(row, kind='td'):

    elts = row.xpath('.//%s' %kind)

 # 根据标签的类型获取数据

    return [val.text_content() for val in elts]

 # 使用列表推导式返回一个列表
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

下面来整合数据并转化为DataFrame类型,pandas提供了一个可以自动类型转换的TextParse类,可以将文本类型自动转换为我们需要的类型。

from pandas.io.parsers import TextParser

def parse_options_data(table):

    rows = table.xpath('.//tr')

 # 以table为当前路径,查找tr标签

    header = _unpack(rows[0], kind='th')

 # 查找th标签作为header

    data = [_unpack(r) for r in rows[1:]]

  # 剩下的行作为data

    return TextParser(data, names=header).get_chunk()

  # 返回一个DataFrame
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19

来测试一下:

content = parse_options_data(tables[0])
  • 1
  nodename                   选取此节点的所有子节点。

0        /                        从根节点选取。

1       //  从匹配选择的当前节点选择文档中的节点,而不考虑它们的位置。

2        .                        选取当前节点。

3       ..                    选取当前节点的父节点。

4        @                          选取属性。
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
本文内容由网友自发贡献,转载请注明出处:https://www.wpsshop.cn/w/运维做开发/article/detail/919685
推荐阅读
相关标签
  

闽ICP备14008679号