前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >02.爬虫基础知识与简易爬虫实现

02.爬虫基础知识与简易爬虫实现

作者头像
qubianzhong
发布2018-08-08 17:09:24
4200
发布2018-08-08 17:09:24
举报
文章被收录于专栏:行者常至行者常至

CSS

基础语法

  • CSS规则:选择器,以及一条或多条声明。 selector {declaration1; ...; desclarationN}
  • 每条声明是由一个属性和一个值组成 property: value
  • 例子 h1 {color: red; font-size: 14px}

元素选择器

  • 直接选择文档元素 比如 head,p
<html>
<head>
<style type="text/css">
    h1 {text-decoration: overline}
    h2 {text-decoration: line-through}
    h3 {text-decoration: underline}
    h4 {text-decoration:blink}
    a {text-decoration: none}
</style>
</head>

<body>
<h1>这是标题 1</h1>
<h2>这是标题 2</h2>
<h3>这是标题 3</h3>
<h4>这是标题 4</h4>
<p><a href="http://www.w3school.com.cn/index.html">这是一个链接</a></p>
</body>

</html>

类选择器

  • 元素的class属性 比如 <h1 class="important">
  • 类名就是important
  • .important选择所有有这个类属性的元素
  • 可以结合元素选择器 比如 p.important
<html>
<head>
<style type="text/css">
    p.serif{font-family:"Times New Roman",Georgia,Serif}
    p.sansserif{font-family:Arial,Verdana,Sans-serif}
</style>
</head>

<body>
<h1>CSS font-family</h1>
<p class="serif">This is a paragraph, shown in the Times New Roman font.</p>
<p class="sansserif">This is a paragraph, shown in the Arial font.</p>

</body>
</html>

ID选择器

  • 元素的id属性 比如 <h1 id="intro">
  • id就是important
  • #intro用于选择id=intro的元素
  • 可以结合元素选择器 比如p.#intro
<html>
<head>
<style type="text/css">
    #serif{font-family:"Times New Roman",Georgia,Serif;color:red}
    #sansserif{font-family:Arial,Verdana,Sans-serif}
</style>
</head>

<body>
<h1>CSS font-family</h1>
<p id="serif">This is a paragraph, shown in the Times New Roman font.</p>
<p id="sansserif">This is a paragraph, shown in the Arial font.</p>

</body>
</html>
与类选择器的异同
  • ID一个文档只能出现一次
  • ID选择器不能使用单词列表
  • 与类选择器一样,都区分大小写。

属性选择器

  • 选择有某个属性的元素,而不论值是什么。
  • *[title] 选择所有包含title属性的元素
  • a[href]选择所有带有href属性的锚元素
  • 还可以选择多个属性,比如:a[href][title],注意这里是要同时满足。
  • 限定值:a[href="www.so.com"]
<html>
<head>
<style type="text/css">
    p.serif{font-family:"Times New Roman",Georgia,Serif;color:red}
    p.serif[title="ttt"]{color:blue}
</style>
</head>

<body>
<h1>CSS font-family</h1>
<p class="serif">testa.</p>
<p class="serif" title="ttt">testb.</p>

</body>
</html>

后代(包含)选择器

  • 选择某元素后代的元素(层级不受限制)
  • 选择h1元素的em元素:h1 em
<html>
<head>
<style type="text/css">
    div em{color:red}
</style>
</head>

<body>
<h1>CSS font-family</h1>
<div>
    <em>test</em>
        <span>
    <em>test2</em>
<span>
</div>

</body>
</html>

子元素选择器

  • 范围限制在子元素
  • 选择h1元素的子元素strong:h1 > strong
<html>
<head>
<style type="text/css">
    div>em{color:red}
</style>
</head>

<body>
<h1>CSS font-family</h1>
<div>
    <em>test</em>
        <span>
    <em>test2</em>
<span>
</div>

</body>
</html>


XPath

节点

  • 七种基本节点
    • 元素、属性、文本
    • 命名空间、处理指令、注释以及根节点
  • 节点之间的关系
    • 父、子、同胞(兄弟)、先辈、后代

路径表达式

  • nodename 选取此节点的所有子节点
  • / 从根节点选取
  • // 从匹配的当前节点选择文档中的节点,而不考虑它们的位置。
  • . 选取当前节点
  • .. 选取当前节点的父节点
  • @ 选取属性

路径表达式例子(参考bookstore.xml文件)

  • bookstore 选取bookstore元素的所有子节点
  • /bookstore 选取根元素bookstore
  • /bookstore/book 选取属于bookstore的子元素的所有book元素
  • //book 选取所有book元素,而不管它们在文档中的位置。
  • bookstore//book 选择属于bookstore元素的后代的所有book元素
  • //@lang 选取名为lang的所有属性

谓语(参考bookstore.xml文件)

  • 嵌在[]中用来查找某个特定节点或包含某个指定值得节点。
  • /bookstore/book[1] 第一个book元素
  • /bookstore/book[last()] 最后一个book元素
  • /bookstore/book[position()<3] 选择前2个
  • //title[@lang] 选择所拥有有名为lang的属性的title元素
  • /bookstore/book[price>35.00]

与CSS选择器的比较

  • CSS更加简洁
  • XPath选择功能更加强大!重点在于层级切换


Json简介

  • 类似XML,但是比 XML 更小、更快,更易解析。
  • 使用json库处理json,编码与解码。
import json

obj = {'one': '一', 'two': '二'}
#把字典解析成JSON
encoded = json.dumps(obj)
print(type(encoded))
print(encoded)
#把JSON解析成字典
decoded = json.loads(encoded)
print(type(decoded))
print(decoded)



Python处理XML方法


book.xml

<?xml version="1.0" encoding="ISO-8859-1"?>
<bookstore>
    <book>
        <title lang="eng">Harry Potter</title>
        <price>29.99</price>
    </book>
    <book>
        <title lang="eng">Learning XML</title>
        <price>39.95</price>
    </book>
</bookstore>

DOM

  • 把整个XML读入内存,解析为树,因此占用内存大,解析慢,优点是可以任意遍历树的节点。
from xml.dom import minidom

doc = minidom.parse('book.xml')
#查找其根节点
root = doc.documentElement
# print(dir(root)) dir 查看其所有方法

#打印根节点的名称
print(root.nodeName)
#查找所有的 book 节点
books = root.getElementsByTagName('book')
print(type(books))
#遍历并获取其节点名称
for book in books:
    titles = book.getElementsByTagName('title')
    prices = book.getElementsByTagName('price')
    print(titles[0].childNodes[0].nodeValue)
    print(prices[0].childNodes[0].nodeValue)


SAX

  • 流模式,边读边解析,占用内存小,解析快,缺点是需要自己处理事件。
import string
from xml.parsers.expat import ParserCreate

class DefaultSaxHandler(object):
    def start_element(self, name, attrs):
        self.element = name
        print('element: %s, attrs: %s' % (name, str(attrs)))

    def end_element(self, name):
        print('end element: %s' % name)

    def char_data(self, text):
        if text.strip():
            print("%s's text is %s" % (self.element, text))

handler = DefaultSaxHandler()
parser = ParserCreate()
parser.StartElementHandler = handler.start_element
parser.EndElementHandler = handler.end_element
parser.CharacterDataHandler = handler.char_data
with open('book.xml', 'r') as f:
    parser.Parse(f.read())



正则表达式入门


基本匹配规则

  • [0-9] 任意一个数字,等价\d
  • [a-z] 任意一个小写字母
  • [A-Z]任意一个大写字母
  • [^0-9] 匹配非数字,等价\D
  • \w 等价[a-z0-9_],字母数字下划线
  • \W 等价对\w取非
  • . 任意字符
  • [] 匹配内部任意字符或子表达式
  • [^] 对字符集合取非

基本匹配规则

  • * 匹配前面的字符或者子表达式0次或多次
  • + 匹配前一个字符至少1次
  • 匹配前一个字符0次或1次
  • ^ 匹配字符串开头
  • $ 匹配字符串结束

Python使用正则表达式

  • re模块
  • match 匹配结果
  • pattern 编译好的正则表达式

import re

# 3位数字-3到8位数字
m = re.match(r'\d{3}\-\d{3,8}', '010-12345')
# print(dir(m))
print(m.string)
print(m.pos, m.endpos)

# 分组
m = re.match(r'^(\d{3})-(\d{3,8})$', '010-12345')
# 分的所有部分 ('010', '12345')
print(m.groups())
# 0 原始数据 010-12345
print(m.group(0))
# 分的第一部分 010
print(m.group(1))
# 分的第二部分 12345
print(m.group(2))

# 分割

p = re.compile(r'\d+') # 分割规则 遇到数字就行分割
print(type(p))
print(p.split('one1two32three3four4'))

t = '20:15:45'
# 分割规则 冒号分割
m = re.match(r'^(0[0-9]|1[0-9]|2[0-3]|[0-9])\:(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])\:(0[0-9]|1[0-9]|2[0-9]|3[0-9]|4[0-9]|5[0-9]|[0-9])$', t)
print(m.groups())



Selenium简介和实战


使用前确认已安装 chromedriver驱动 并将 chromedriver.exe 的路径设置为环境变量请确保安装的最新的驱动,不然可能会报错。


关键命令

find_element(s)_by_tag_name
find_element(s)_by_css_selector

电商网站数据爬取

from selenium import webdriver
import time

#声明使用chrome的驱动器
browser = webdriver.Chrome()
#设置等待超时,不超过30秒
browser.set_page_load_timeout(30)
#打开页面
browser.get('http://www.17huo.com/search.html?sq=2&keyword=羊毛')
#检查总共有多少页 
page_info = browser.find_element_by_css_selector('body > div.wrap > div.pagem.product_list_pager > div')
# print(page_info.text)
# 共 100 页,每页 24 条
pages = int((page_info.text.split(',')[0]).split(' ')[1])
for page in range(pages):
    if page > 2:
        break
    url = 'http://www.17huo.com/?mod=search&sq=2&keyword=%E7%BE%8A%E6%AF%9B&page=' + str(page + 1)
    browser.get(url)
    #此页面动态加载,此处模拟 滑轮滚动 页面下滑
    browser.execute_script("window.scrollTo(0, document.body.scrollHeight);")
    time.sleep(2)   # 不然会load不完整
    goods = browser.find_element_by_css_selector('body > div.wrap > div:nth-child(2) > div.p_main > ul').find_elements_by_tag_name('li')
    print('%d页有%d件商品' % ((page + 1), len(goods)))
    for good in goods:
        try:
            title = good.find_element_by_css_selector('a:nth-child(1) > p:nth-child(2)').text
            price = good.find_element_by_css_selector('div > a > span').text
            print(title, price)
        except:
            print("Exception...........")

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2018年06月08日,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • CSS
    • 基础语法
      • 元素选择器
        • 类选择器
          • ID选择器
            • 属性选择器
              • 后代(包含)选择器
                • 子元素选择器
                • XPath
                  • 节点
                    • 路径表达式
                      • 路径表达式例子(参考bookstore.xml文件)
                        • 谓语(参考bookstore.xml文件)
                          • 与CSS选择器的比较
                          • Json简介
                          • Python处理XML方法
                            • DOM
                              • SAX
                              • 正则表达式入门
                                • 基本匹配规则
                                  • 基本匹配规则
                                    • Python使用正则表达式
                                    • Selenium简介和实战
                                      • 使用前确认已安装 chromedriver驱动 并将 chromedriver.exe 的路径设置为环境变量。请确保安装的最新的驱动,不然可能会报错。
                                        • 关键命令
                                          • 电商网站数据爬取
                                          领券
                                          问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档