【问题标题】:Scraping an html table, how to have the info in a similar structure抓取一个 html 表,如何以类似的结构获取信息
【发布时间】:2014-09-01 17:08:18
【问题描述】:

我正在尝试抓取一个看起来像这样的 html 表格:

Recent ratings:
thew              26-6-2014 11:02     Karma   +4      lucky you
user34            26-6-2014 10:34     Karma   +3      great!
godspeed          26-6-2014 06:50     Karma   +5      thanks!
                                                                [Report to Mod.]

我使用 Beautiful Soup,我的代码包括:

five = soup.findAll("fieldset")

for html in five:
            text5 = BeautifulSoup(str(html).strip()).get_text().encode("utf-8").replace("   ", "")
            karmas.append(text5.split("Recent Ratings")[1].split("[Report to Mod.]")[0].strip())

结果,在 csv 文件中,有一列如下所示:

thew
ᅡᅠᅡᅠ26-6-2014 11:02ᅡᅠᅡᅠKarmaᅡᅠᅡᅠ+4
ᅡᅠᅡᅠlucky you
user34
ᅡᅠᅡᅠ26-6-2014 10:34ᅡᅠᅡᅠKarmaᅡᅠᅡᅠ+3
ᅡᅠᅡᅠgreat!
godspeed
ᅡᅠᅡᅠ26-6-2014 06:50ᅡᅠᅡᅠKarmaᅡᅠᅡᅠ+5
ᅡᅠᅡᅠthanks!

如何在类似于表格的结构中分离信息?

我尝试添加.replace("\n", ""),结果是一行中的所有信息:

thewᅡᅠᅡᅠ26-6-2014 11:02ᅡᅠᅡᅠKarmaᅡᅠᅡᅠ+4ᅡᅠᅡᅠlucky youuser34ᅡᅠᅡᅠ26-6-2014 10:34ᅡᅠᅡᅠKarmaᅡᅠᅡᅠ+3ᅡᅠᅡᅠgreat!godspeedᅡᅠᅡᅠ26-6-2014 06:50ᅡᅠᅡᅠKarmaᅡᅠᅡᅠ+5ᅡᅠᅡᅠthanks!

这是我打印“五”时得到的结果。

[<fieldset><legend><a href="misc.php?action=viewratings&amp;tid=50510&amp;pid=502926" title="View Rating Log">Recent Ratings</a></legend><br/>
<table border="0" cellpadding="0" cellspacing="0">
<tr><td><a href="viewpro.php?uid=21445" target="_blank">thew</a></td>
<td>  26-6-2014 11:02</td><td>  Karma</td><td>  <b>+4</b></td>
<td>  lucky you</td></tr>
<tr><td><a href="viewpro.php?uid=43867" target="_blank">user34</a></td>
<td>  26-6-2014 10:34</td><td>  Karma</td><td>  <b>+3</b></td>
<td>  great!</td></tr>
<tr><td><a href="viewpro.php?uid=68709" target="_blank">godspeed</a></td>
<td>  26-6-2014 06:50</td><td>  Karma</td><td>  <b>+5</b></td>
<td>  thanks!</td></tr>
</table>
</fieldset>]

下面的答案在我打印输出时有效,但在我将其写入 csv 时无效。摘自我的代码:

five = soup.findAll("fieldset")

karmas = []

for i in five:
    for j in  i.findAll('td'):
        somevar = j.text
        print somevar           
        karmas.append(somevar.strip())

        csvfile = open('test.csv', 'ab')    
        writer = csv.writer(csvfile)

        for karma in zip(karmas):
                writer.writerow([karma])

        csvfile.close()

#output print somevar

thew
  26-6-2014 11:02
  Karma
  +4
  lucky you
user34
  26-6-2014 10:34
  Karma
  +3
  great!
godspeed
  26-6-2014 06:50
  Karma
  +5
  thanks!

# output in csv

thew

【问题讨论】:

  • 如果能在这里给出five的输出会更容易理解。
  • 感谢您的回复!我刚刚添加了您要求的内容。

标签: python python-2.7 web-scraping beautifulsoup


【解决方案1】:

在字段集中使用soup.findAll("tr") 而不是soup.findAll("fieldset")

html=''' <fieldset><legend><a href="misc.php?action=viewratings&amp;tid=50510&amp;pid=502926" title="View Rating Log">Recent Ratings</a></legend><br/>
<table border="0" cellpadding="0" cellspacing="0">
<tr><td><a href="viewpro.php?uid=21445" target="_blank">thew</a></td>
<td>  26-6-2014 11:02</td><td>  Karma</td><td>  <b>+4</b></td>
<td>  lucky you</td></tr>
<tr><td><a href="viewpro.php?uid=43867" target="_blank">user34</a></td>
<td>  26-6-2014 10:34</td><td>  Karma</td><td>  <b>+3</b></td>
<td>  great!</td></tr>
<tr><td><a href="viewpro.php?uid=68709" target="_blank">godspeed</a></td>
<td>  26-6-2014 06:50</td><td>  Karma</td><td>  <b>+5</b></td>
<td>  thanks!</td></tr>
</table>
</fieldset> '''

from bs4 import BeautifulSoup
import csv

soup=BeautifulSoup(html)
five = soup.findAll("tr")
for i in five:
    with open('some.csv', 'a') as f:
        writer = csv.writer(f)

        writer.writerow([j.text for j in  i.findAll('td')])

#output

thew   26-6-2014 11:02   Karma  +4   lucky you
user34   26-6-2014 10:34   Karma  +3   great!
godspeed   26-6-2014 06:50   Karma  +5   thanks!

【讨论】:

  • 看起来这可行,但仅在这三个用户的特定示例中?我需要对数千个 html 文件执行此操作,这些文件的反馈会来自不同的用户。
  • 代码完全独立于数据。如果 html 文件具有相同的结构,这应该会为任何文件上的任意数量的用户取消评论。
  • 啊,我明白了,谢谢!如上所述,它在打印时绝对有效。但是,当我尝试将其写入我的 csv 时,输出只是“thew”,即第一个用户的名称——所有内容都被遗漏了。我已经更新了我上面的问题来解释!
  • Sundar,对如何将文本转换为 csv 有什么想法吗?请参阅更新的问题。我希望你能帮忙!
  • 感谢桑达尔的帮助!
猜你喜欢
  • 2019-07-16
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-08-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多