BeautifulSoup Parse T的深度优先遍历

2024-06-16 10:42:29 发布

您现在位置:Python中文网/ 问答频道 /正文

有没有办法在漂亮的组解析树上进行DFT?我尝试从根开始,通常是获取所有子元素,然后为每个子元素获取它们的子元素,等等,直到我到达一个终端节点,在这个节点上,我将建立我的方法备份到树上。问题是我似乎找不到一种方法能让我这么做。我找到了findChildren方法,但这似乎只是将整个页面多次放入列表中,每个后续条目都会减少。我可能可以使用这个来进行遍历,但是除了列表中的最后一个条目之外,似乎没有任何方法可以将条目标识为终端节点。有什么想法吗?


Tags: 方法终端元素列表节点条目页面备份
2条回答

recursiveChildGenerator()已经做到了:

soup = BeautifulSoup.BeautifulSoup(html)
for child in soup.recursiveChildGenerator():
     name = getattr(child, "name", None)
     if name is not None:
         print name
     elif not child.isspace(): # leaf node, don't print spaces
         print child

输出

对于来自@msalvadores's answer的html:

html
ul
li
Lorem ipsum dolor sit amet, consectetuer adipiscing elit.
li
Aliquam tincidunt mauris eu risus.
li
Vestibulum auctor dapibus neque.
html

注意:html由于the example包含两个打开的<html>标记而打印两次。

我认为您可以使用“childGenerator”方法并递归地使用这个方法以DFT的方式解析树。

def recursiveChildren(x):
   if "childGenerator" in dir(x):
      for child in x.childGenerator():
          name = getattr(child, "name", None)
          if name is not None:
             print "[Container Node]",child.name
          recursiveChildren(child)
    else:
       if not x.isspace(): #Just to avoid printing "\n" parsed from document.
          print "[Terminal Node]",x

if __name__ == "__main__":
    soup = BeautifulSoup(your_data)
    for child in soup.childGenerator():
        recursiveChildren(child)

使用"childGenerator" in dir(x)我们确保元素是容器,终端节点(如NavigableStrings)不是容器,也不包含子节点。

例如HTML:

<html>
<ul>
   <li>Lorem ipsum dolor sit amet, consectetuer adipiscing elit.</li>
   <li>Aliquam tincidunt mauris eu risus.</li>
   <li>Vestibulum auctor dapibus neque.</li>
</ul>
</html>

这些脚本打印。。。

[Container Node] ul
[Container Node] li
[Terminal Node] Lorem ipsum dolor sit amet, consectetuer adipiscing elit.
[Container Node] li
[Terminal Node] Aliquam tincidunt mauris eu risus.
[Container Node] li
[Terminal Node] Vestibulum auctor dapibus neque.

相关问题 更多 >