如何在Python中将HTML表格转换为数组

15 投票
3 回答
35365 浏览
提问于 2025-04-15 22:55

我有一个HTML文档,我想把里面的表格提取出来,并把它们返回为数组。我想象着有两个函数,一个是用来找到文档中的所有HTML表格,另一个是把HTML表格转换成二维数组。

大概是这样的:

htmltables = get_tables(htmldocument)
for table in htmltables:
    array=make_array(table)

不过有两个问题需要注意:

  1. 表格的数量每天都不一样。
  2. 表格里面有各种奇怪的额外格式,比如加粗和闪烁标签,随意混在里面。

谢谢!

3 个回答

1

给提问的人加个赞,也给Python的大神加个赞。
我想用lxml和CSS选择器来试试这个例子。
是的,这个基本上和Alex的例子差不多:

import lxml.html
markup = lxml.html.fromstring('''<html><body>\
<table width="600">
    <tr>
        <td width="50%">0,0,0</td>
        <td width="50%">0,0,1</td>
    </tr>
    <tr>
        <td>0,1,0</td>
        <td>0,1,1</td>
    </tr>
</table>
<table>
    <tr>
        <td>1,0,0</td>
        <td>1,<blink>0,</blink>1</td>
        <td>1,0,2</td>
        <td><bold>1</bold>,0,3</td>
    </tr>
</table>
</body></html>''')

tbl = []
rows = markup.cssselect("tr")
for row in rows:
  tbl.append(list())
  for td in row.cssselect("td"):
    tbl[-1].append(unicode(td.text_content()))

pprint(tbl)
#[[u'0,0,0', u'0,0,1'],
# [u'0,1,0', u'0,1,1'],
# [u'1,0,0', u'1,0,1', u'1,0,2', u'1,0,3']]
21

使用BeautifulSoup(我推荐使用3.0.8版本)。找到所有的表格非常简单:

import BeautifulSoup

def get_tables(htmldoc):
    soup = BeautifulSoup.BeautifulSoup(htmldoc)
    return soup.findAll('table')

不过,在Python中,数组是单维的,而且只能包含一些基本类型的元素(比如整数、浮点数,简单得很)。所以,没办法把一个HTML表格放进Python的array里。

你可能是想说Python的list吧?这也是单维的,但里面的元素可以是任何东西,所以你可以有一个列表里面包含多个列表(我想每个子列表对应一个tr标签,里面每个元素对应一个td标签)。

这样就能得到:

def makelist(table):
  result = []
  allrows = table.findAll('tr')
  for row in allrows:
    result.append([])
    allcols = row.findAll('td')
    for col in allcols:
      thestrings = [unicode(s) for s in col.findAll(text=True)]
      thetext = ''.join(thestrings)
      result[-1].append(thetext)
  return result

这可能还不是你想要的(没有跳过HTML注释,子列表里的元素是unicode字符串而不是字节字符串等等),但应该很容易调整。

11

Pandas 是一个很方便的工具,它可以直接从你的网页中提取所有的表格,并把它们放到一个数据框的列表里,这样你就不用自己去解析网页了,省去了很多麻烦。一个数据框(DataFrame)是一种强大的二维数组类型。

我建议你继续使用Pandas来处理数据,因为它非常好用。不过,如果你喜欢的话,也可以把数据转换成其他格式,比如列表、字典、CSV文件等等。

示例

"""Extract all tables from an html file, printing and saving each to csv file."""

import pandas as pd

df_list = pd.read_html('my_file.html')

for i, df in enumerate(df_list):
    print df
    df.to_csv('table {}.csv'.format(i))

如果你想直接从网上获取HTML内容,而不是从文件中读取,只需要稍微修改一下代码:

import requests

html = requests.get('my_url').content
df_list = pd.read_html(html)

撰写回答