如何从BeautifulSoup的表中获取第一个和第三个td?

Ale*_*tay 5 html python html-table beautifulsoup html-parsing

我目前正在使用Python和BeautifulSoup来抓取一些网站数据.我正在尝试从表格中拉出单元格,格式如下:

<tr><td>1<td><td>20<td>5%</td></td></td></td></tr>
Run Code Online (Sandbox Code Playgroud)

上述HTML的问题在于BeautifulSoup将其作为一个标记读取.我需要从第一个<td>和第三个中提取值<td>,分别为1和20.

不幸的是,我不知道如何解决这个问题.如何让BeautifulSoup读取<td>表格每行的第1和第3个标签?

更新:

我解决了这个问题.我正在使用html.parser而不是BeautifulSoup的默认值.一旦我切换到默认值,问题就消失了.我也使用了答案中列出的方法.

我还发现不同的解析器非常具有破坏代码的气质.例如,默认解析器拒绝阅读过去排192,但html5lib得到了这份工作done.So尝试使用lxml,html以及还html5lib如果您有分析整个表的问题.

Zer*_*eus 10

这是一个令人讨厌的HTML,你已经到了那里.如果我们暂时忽略表行和表单元格的语义并将其视为纯XML,其结构如下所示:

<tr>
  <td>1
    <td>
      <td>20
        <td>5%</td>
      </td>
    </td>
  </td>
</tr>
Run Code Online (Sandbox Code Playgroud)

然而,BeautifulSoup知道HTML表的语义,而是像这样解析它:

<tr>
  <td>1        <!-- an IMPLICITLY (no closing tag) closed td element -->
  <td>         <!-- as above -->
  <td>20       <!-- as above -->
  <td>5%</td>  <!-- an EXPLICITLY closed td element -->
  </td>        <!-- an error; ignore this -->
  </td>        <!-- as above -->
  </td>        <!-- as above -->
</tr>
Run Code Online (Sandbox Code Playgroud)

......所以,正如你所说,1和20分别位于第一和第三个td元素(不是标签)中.

你实际上可以得到这些td元素的内容,如下所示:

>>> from bs4 import BeautifulSoup
>>> soup = BeautifulSoup("<tr><td>1<td><td>20<td>5%</td></td></td></td></tr>")
>>> tr = soup.find("tr")
>>> tr
<tr><td>1</td><td></td><td>20</td><td>5%</td></tr>
>>> td_list = tr.find_all("td")
>>> td_list
[<td>1</td>, <td></td>, <td>20</td>, <td>5%</td>]
>>> td_list[0]  # Python starts counting list items from 0, not 1
<td>1</td>
>>> td_list[0].text
'1'
>>> td_list[2].text
'20'
>>> td_list[3].text
'5%'
Run Code Online (Sandbox Code Playgroud)