Python beautifulsoup迭代在桌子上

Wil*_*ill 14 python beautifulsoup

我试图将表数据刮到CSV文件中.不幸的是,我遇到了一个障碍,下面的代码只是从第一个TR重复所有后续TR的TD.

import urllib.request
from bs4 import BeautifulSoup

f = open('out.txt','w')

url = "http://www.international.gc.ca/about-a_propos/atip-aiprp/reports-rapports/2012/02-atip_aiprp.aspx"
page = urllib.request.urlopen(url)

soup = BeautifulSoup(page)

soup.unicode

table1 = soup.find("table", border=1)
table2 = soup.find('tbody')
table3 = soup.find_all('tr')

for td in table3:
    rn = soup.find_all("td")[0].get_text()
    sr = soup.find_all("td")[1].get_text()
    d = soup.find_all("td")[2].get_text()
    n = soup.find_all("td")[3].get_text()

    print(rn + "," + sr + "," + d + ",", file=f)
Run Code Online (Sandbox Code Playgroud)

这是我的第一个Python脚本,所以任何帮助将不胜感激!我已经查看了其他问题的答案,但无法弄清楚我在这里做错了什么.

kin*_*all 39

你每次使用开始在文档的顶层find()或者find_all(),所以当你要求,例如,所有的"TD"`标签你得到所有的"TD"标签的文档中,不只是那些在您搜索的表和行中.您也可以不搜索那些因为它们没有按照您的代码编写方式使用.

我想你想做这样的事情:

table1 = soup.find("table", border=1)
table2 = table1.find('tbody')
table3 = table2.find_all('tr')
Run Code Online (Sandbox Code Playgroud)

或者,你知道,更像这样的东西,更具描述性的变量名称来引导:

rows = soup.find("table", border=1).find("tbody").find_all("tr")

for row in rows:
    cells = row.find_all("td")
    rn = cells[0].get_text()
    # and so on
Run Code Online (Sandbox Code Playgroud)


And*_*ter 7

问题在于,每当你试图缩小你的搜索范围时(在这个tr中得到第一个td等),你只需要回电话给汤.汤是顶级对象 - 它代表整个文档.你只需要打一次汤,然后用它的结果代替汤来进行下一步.

例如(变量​​名称变得更清楚),

table = soup.find('table', border=1)
rows = table.find_all('tr')

for row in rows:
    data = row.find_all("td")
    rn = data[0].get_text()
    sr = data[1].get_text()
    d = data[2].get_text()
    n = data[3].get_text()

    print(rn + "," + sr + "," + d + ",", file=f)
Run Code Online (Sandbox Code Playgroud)

我不确定print语句是你在这里尝试做什么的最佳方式(至少,你应该使用字符串格式而不是添加),但我将它保留原样,因为它不是核心问题.

此外,完成: soup.unicode不会做任何事情.你没有在那里调用一个方法,也没有任何作业.我不记得BeautifulSoup首先有一个名为unicode的方法,但我已经习惯了BS 3.0,因此它可能是4中的新功能.