貓哥教你寫爬蟲 039--存儲數據

1559362140604

存儲到mysql數據庫

咱們須要新的模塊 pymysql

pip install pymysql
複製代碼

1559364775960

建立數據庫book_store

create database book_store character set utf8;
複製代碼

建立category分類表, 包含id和分類名

use book_store;
create table category(
    id int primary key auto_increment, 
    name varchar(255) not null
);
複製代碼

建立數據表book, 包含id,分類id,圖書名,價格, 還有外鍵

create table book(
	id int primary key auto_increment,
    cid int not null,
    title varchar(200) not null,
    price decimal(10,2) not null,
    foreign key(cid) references category(id)
);
複製代碼
mysql> desc category;
+-------+--------------+------+-----+---------+----------------+
| Field | Type         | Null | Key | Default | Extra          |
+-------+--------------+------+-----+---------+----------------+
| id    | int(11)      | NO   | PRI | NULL    | auto_increment |
| name  | varchar(255) | NO   |     | NULL    |                |
+-------+--------------+------+-----+---------+----------------+
mysql> desc book;
+-------+---------------+------+-----+---------+----------------+
| Field | Type          | Null | Key | Default | Extra          |
+-------+---------------+------+-----+---------+----------------+
| id    | int(11)       | NO   | PRI | NULL    | auto_increment |
| cid   | int(11)       | NO   | MUL | NULL    |                |
| title | varchar(200)  | NO   |     | NULL    |                |
| price | decimal(10,2) | NO   |     | NULL    |                |
+-------+---------------+------+-----+---------+----------------+
4 rows in set (0.02 sec)
複製代碼

使用python把爬取的數據保存到數據庫

原來的代碼...

import requests
from bs4 import BeautifulSoup
soup = BeautifulSoup(requests.get('http://books.toscrape.com/').text,'html.parser')
with open('books.txt','w',encoding='utf8') as file:
    for i in soup.find('ul',class_='nav nav-list').find('ul').find_all('li'):
        file.write(i.text.strip()+'\n')
        res = requests.get("http://books.toscrape.com/"+i.find('a')['href'])
        res.encoding='utf8'
        soup = BeautifulSoup(res.text,'html.parser')
        for j in soup.find_all('li',class_="col-xs-6 col-sm-4 col-md-3 col-lg-3"):
            print(j.find('h3').find('a')['title'])
            file.write('\t"{}" {}\n'.format(j.find('h3').find('a')['title'],j.find('p',class_='price_color').text))
複製代碼

進行一下注釋和改進

import requests
from bs4 import BeautifulSoup
soup = BeautifulSoup(requests.get('http://books.toscrape.com/').text,'html.parser')
for i in soup.find('ul',class_='nav nav-list').find('ul').find_all('li'):
    category = i.text.strip() # 分類名
    print(category)
    res = requests.get("http://books.toscrape.com/"+i.find('a')['href'])
    res.encoding='utf8'
    soup = BeautifulSoup(res.text,'html.parser')
    for j in soup.find_all('li',class_="col-xs-6 col-sm-4 col-md-3 col-lg-3"):
        title = j.find('h3').find('a')['title'] # 圖書名
        price = j.find('p',class_='price_color').text # 圖書價格
複製代碼

研究一下pymysql 的使用方法

shockerli.net/post/python…

建立mysql鏈接

import pymysql
connection = pymysql.connect(host='localhost',
                             port=3306,
                             user='root',
                             password='root',
                             db='demo',
                             charset='utf8')
複製代碼

生成遊標, 執行sql語句...

# 獲取遊標
cursor = connection.cursor()
    
# 建立數據表
effect_row = cursor.execute(''' CREATE TABLE `users` ( `name` varchar(32) NOT NULL, `age` int(10) unsigned NOT NULL DEFAULT '0', PRIMARY KEY (`name`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 ''')
    
# 插入數據(元組或列表)
effect_row = cursor.execute('INSERT INTO `users` (`name`, `age`) VALUES (%s, %s)', ('mary', 18))
    
# 插入數據(字典)
info = {'name': 'fake', 'age': 15}
effect_row = cursor.execute('INSERT INTO `users` (`name`, `age`) VALUES (%(name)s, %(age)s)', info)
    
connection.commit()
複製代碼

一次性執行多條sql語句

# 獲取遊標
cursor = connection.cursor()
    
# 批量插入
effect_row = cursor.executemany(
    'INSERT INTO `users` (`name`, `age`) VALUES (%s, %s) ON DUPLICATE KEY UPDATE age=VALUES(age)', [
        ('hello', 13),
        ('fake', 28),
    ])
    
connection.commit()
複製代碼

獲取自增id

cursor.lastrowid
複製代碼

查詢數據, 一條或者多條

# 執行查詢 SQL
cursor.execute('SELECT * FROM `users`')
# 獲取單條數據
cursor.fetchone()
# 獲取前N條數據
cursor.fetchmany(3)
# 獲取全部數據
cursor.fetchall()
複製代碼

思路分析

代碼拆解

面向對象的寫法...

import requests
from bs4 import BeautifulSoup
import pymysql
class Spider():
    def __init__(self, base_url):
        self.base_url = base_url
        self.db = Database('localhost', 'root', 'root', 'book_store')
        self.soup = BeautifulSoup(requests.get(
            self.base_url).text, 'html.parser')
    def get_category(self):
        for i in self.soup.find('ul', class_='nav nav-list').find('ul').find_all('li'):
            category = i.text.strip()  # 分類名
            self.db.add_category(category)
            self.db.book_link_dict[category] = "http://books.toscrape.com/"+i.find('a')[
                'href']
    def get_book(self):
        for cat in self.db.book_link_dict:
            res = requests.get(self.db.book_link_dict[cat])
            res.encoding = 'utf8'
            soup = BeautifulSoup(res.text, 'html.parser')
            for j in soup.find_all('li', class_="col-xs-6 col-sm-4 col-md-3 col-lg-3"):
                title = j.find('h3').find('a')['title']  # 圖書名
                price = j.find('p', class_='price_color').text[1:]  # 圖書價格
                self.db.add_book(cat, title, price)
    def start(self):
        self.get_category()
        self.get_book()
class Database():
    category_dict = {}
    book_link_dict = {}
    def __init__(self, host, username, password, db):
        self.connect = pymysql.connect(
            host=host, port=3306, user=username, password=password, db=db, charset='utf8'
        )
        self.cursor = self.connect.cursor()
    def add_category(self, name):
        sql = "insert into `category`(`name`) values('{}')".format(name)
        print(sql)
        self.cursor.execute(sql)
        self.connect.commit()
        last_id = self.cursor.lastrowid
        self.category_dict[name] = last_id
        return last_id
    def add_book(self, category, title, price):
        if category in self.category_dict:
            cid = self.category_dict[category]
        else:
            cid = self.add_category(category)
        sql = "insert into `book`(`cid`,`title`,`price`) values({},{},{})".format(
            cid, repr(title), price)
        print(sql)
        self.cursor.execute(sql)
        self.connect.commit()
        return self.cursor.lastrowid
if __name__ == "__main__":
    spider = Spider('http://books.toscrape.com/')
    spider.start()
複製代碼

1559375044484

小做業:爬取貓眼電影top100, 保存 電影名, 排名, 評分, 主演, 封面圖片, 上映時間到數據庫

maoyan.com/board/4

1559375538602

快速跳轉:

貓哥教你寫爬蟲 000--開篇.md
貓哥教你寫爬蟲 001--print()函數和變量.md
貓哥教你寫爬蟲 002--做業-打印皮卡丘.md
貓哥教你寫爬蟲 003--數據類型轉換.md
貓哥教你寫爬蟲 004--數據類型轉換-小練習.md
貓哥教你寫爬蟲 005--數據類型轉換-小做業.md
貓哥教你寫爬蟲 006--條件判斷和條件嵌套.md
貓哥教你寫爬蟲 007--條件判斷和條件嵌套-小做業.md
貓哥教你寫爬蟲 008--input()函數.md
貓哥教你寫爬蟲 009--input()函數-人工智能小愛同窗.md
貓哥教你寫爬蟲 010--列表,字典,循環.md
貓哥教你寫爬蟲 011--列表,字典,循環-小做業.md
貓哥教你寫爬蟲 012--布爾值和四種語句.md
貓哥教你寫爬蟲 013--布爾值和四種語句-小做業.md
貓哥教你寫爬蟲 014--pk小遊戲.md
貓哥教你寫爬蟲 015--pk小遊戲(全新改版).md
貓哥教你寫爬蟲 016--函數.md
貓哥教你寫爬蟲 017--函數-小做業.md
貓哥教你寫爬蟲 018--debug.md
貓哥教你寫爬蟲 019--debug-做業.md
貓哥教你寫爬蟲 020--類與對象(上).md
貓哥教你寫爬蟲 021--類與對象(上)-做業.md
貓哥教你寫爬蟲 022--類與對象(下).md
貓哥教你寫爬蟲 023--類與對象(下)-做業.md
貓哥教你寫爬蟲 024--編碼&&解碼.md
貓哥教你寫爬蟲 025--編碼&&解碼-小做業.md
貓哥教你寫爬蟲 026--模塊.md
貓哥教你寫爬蟲 027--模塊介紹.md
貓哥教你寫爬蟲 028--模塊介紹-小做業-廣告牌.md
貓哥教你寫爬蟲 029--爬蟲初探-requests.md
貓哥教你寫爬蟲 030--爬蟲初探-requests-做業.md
貓哥教你寫爬蟲 031--爬蟲基礎-html.md
貓哥教你寫爬蟲 032--爬蟲初體驗-BeautifulSoup.md
貓哥教你寫爬蟲 033--爬蟲初體驗-BeautifulSoup-做業.md
貓哥教你寫爬蟲 034--爬蟲-BeautifulSoup實踐.md
貓哥教你寫爬蟲 035--爬蟲-BeautifulSoup實踐-做業-電影top250.md
貓哥教你寫爬蟲 036--爬蟲-BeautifulSoup實踐-做業-電影top250-做業解析.md
貓哥教你寫爬蟲 037--爬蟲-寶寶要聽歌.md
貓哥教你寫爬蟲 038--帶參數請求.md
貓哥教你寫爬蟲 039--存儲數據.md
貓哥教你寫爬蟲 040--存儲數據-做業.md
貓哥教你寫爬蟲 041--模擬登陸-cookie.md
貓哥教你寫爬蟲 042--session的用法.md
貓哥教你寫爬蟲 043--模擬瀏覽器.md
貓哥教你寫爬蟲 044--模擬瀏覽器-做業.md
貓哥教你寫爬蟲 045--協程.md
貓哥教你寫爬蟲 046--協程-實踐-吃什麼不會胖.md
貓哥教你寫爬蟲 047--scrapy框架.md
貓哥教你寫爬蟲 048--爬蟲和反爬蟲.md
貓哥教你寫爬蟲 049--完結撒花.mdhtml

相關文章
相關標籤/搜索