index.html页面内容:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<html>
   <head>
       <meta name="meta_name" content="meta_content" charset="UTF-8">
       <title>测试html内容</title>
   </head>
   
<body>
       <h2>hello everyone!</h2>
       <p class="title">今日天气:晴转多云</p>
       <div id="left" class="content">左边标题</div>
       <div id="right" class="content">
          网址一:<a class="link" href="#link1">www.example1.com</a>
          网址二:<a class="link" href="#link2">www.example2.com</a>
       </div>
       <div class="end">底部内容</div>
   </body>
</html>

Beautiful Soup的使用

初始化页面

1
2
3
4
5
6
from bs4 import BeautifulSoup

with open("index.html", "r") as f:
   html = f.read()
   
soup = BeautifulSoup(html, "html.parser")

获取h2标签

1
2
3
4
h2 = soup.select("h2")
# 或
h2 = soup.find_all("h2")
print(h2)

结果:

1
[<h2>hello everyone!</h2>]

获取所有div

1
2
3
4
divs = soup.select("div")
# 或
divs = soup.find_all("div")
print(divs)

结果:

1
2
3
4
[<div class="content" id="left">左边标题</div>, <div class="content" id="right">
网址一:<a class="link" href="#link1">www.example1.com</a>
网址二:<a class="link" href="#link2">www.example2.com</a>
</div>, <div class="end">底部内容</div>]

获取class=”content”的div内容

1
2
3
divs = soup.find_all("div", class_="content")	# 获取div id=left的内容
text = divs[0].text
print(text)

结果:

1
'左边标题'

获取网址一的链接内容

1
2
3
a = soup.find_all("a", class_="link")
href = a[0]["href"] # 获取meta 属性content的值
print(href)

结果:

1
'#link1'

获取meta属性content的值

1
2
3
meta = soup.find("meta")
content = meta["content"]
print(content)

结果:

1
'meta_content'

lxml的使用

初始化页面

1
2
3
4
5
from lxml import etree
with open("index.html", "r") as f:
   html = f.read()
   
selector = etree.HTML(text)    # 初始化生成一个XPath解析对象

获取h2中的内容

1
2
h2 = selector.xpath("//h2")
h2_text = h2[0].text # 获取div id=left的class属性值和内容

结果:

1
'hello everyone!'

获取div id=left的class属性值和内容

1
2
3
4
div = selector.xpath("//div[@id='left']")    # 获取div id=left节点
content = div[0].get("class")    # 获取class属性值
text = div[0].text        # 获取该节点的内容
print(content, text)

结果:

1
'content' '左边标题'

获取所有div

1
2
divs = selector.xpath("//div")	# 获取div class=content的节点
print(divs)

结果:

1
2
3
[<Element div at 0x7f1368093648>,
<Element div at 0x7f136856d988>,
<Element div at 0x7f1363fe2708>]

获取div class=content的节点

1
2
divs = selector.xpath("//div[@class='content']") # 获取网站一的连接内容和链接
print(divs)

结果:

1
[<Element div at 0x7f1368093648>, <Element div at 0x7f136856d988>]

获取网站一的连接内容和链接

1
2
3
4
par_a = selector.xpath("//div[@id='right']")    # 连接a节点的父节点
a = par_a[0].getchildren()[0].text        # 获取该父节点的第一个子节点的内容
a_href = par_a[0].getchildren()[0].get("href")    # 获取链接
print(a, a_href)

结果:

1
'www.example1.com' '#link1'

获取meta的content属性值

1
2
3
meta = selector.xpath("//meta[@name='meta_name']")    # 获取meta节点
content = meta[0].get("content")
print(content)

结果:

1
'meta_content'

获取所有网址的内容

1
2
3
web = selector.xpath("//a[@class='link']")
for i in web:
   print(i.text)

结果:

1
2
www.example1.com
www.example2.com

以上遍历HTML内容大致信息也就如此,基本上满足一般的使用。更详细信息请参照bs4官方文档 以及 lxml文档

附加:CSS选择器

index.html文件内容不变,我们先加载html:

1
2
3
4
5
6
7
8
from scrapy.selector import Selector
from scrapy.http import HtmlResponse

with open('index.html', 'r') as f:
html = f.read()

# 创建response对象
response = HtmlResponse(url="http://www.example.com", body=html, encoding="utf-8")

获取h2中的内容

1
text = response.css('h2::text').extract_first()

获取div id=left的class属性值和内容

1
2
3
4
5
6
7
# 方法一
div = response.css('div[id="left"]').extract_first() # 获取该div元素
class_ = div.attrib.get('class') # 获取属性class的值
# 方法二
class_ = response.css('div[id="left"]::attr("class")').extract_first()
# 获取内容
content = response.css('div[id="left"]::text').extract_first()

获取所有div

1
divs = response.css('div')

获取div class=content的节点

1
divs = response.css('div[class=content]')

获取网站一的链接内容和链接

1
2
3
4
5
6
7
# 网站一的链接内容
a_text = response.css('div[id="right"]>a:nth-child(1)::text').extract_first()
# 链接
a = response.css('div[id="right"]>a:nth-child(1)')
href = a.attrib.get('href')
# 或者
href = response.css('div[id="right"]>a:nth-child(1)::attr("href")').extract_first()

获取meta的content属性值

1
2
3
4
meta = response.css('meta[name="meta_name"]')	# 获取meta元素
content = meta.attrib.get("content") # 或值
# 方法二
content = response.css('meta[name="meta_name"]::attr("content")').extract_first()

获取所有网址的内容

1
a_texts = response.css('div[id="right"]>a::text').extract()