Python爬虫数据到sqlite实例

  • Post author:
  • Post category:python


参考链接:

https://blog.csdn.net/qq_45775027/article/details/115319253

最近需要使用到爬虫+数据库,原文中作者有些没补齐,略作修改之后跑通了。

主要修改:

1.调整了数据获取的正则表达式;

2. 改了一下数据库的table名和定义名字;

3.加了数据清洗的模块;

实现了爬取qs大学排名,以及存储数据到数据库。


1.效果如下图:


2.使用工具以及环境:

python3.7环境,数据库软件navicat161_premium_en_x86.exe。

一键运行代码,生成对应的db文件,查看内容,和预期一致。


3.完整代码如下:

##参考链接:https://blog.csdn.net/qq_45775027/article/details/115319253

import sqlite3
import re
import time
import requests
from lxml import html

findNameData = re.compile(r'<td style="outline: none !important;">(.*?)</td>')
                         
# =============================================================================
# findname = re.compile(r'<a href=".*?">(.*?)</a>')
# findname3 = re.compile(
#     r'<td style="outline: 0px !important;"><p style="line-height: 1.8; outline: 0px !important;">(.*?)</p></td>')
# findname4 = re.compile(
#     r'<td style="outline: 0px !important;"><p style="line-height: 1.8; outline: 0px !important;"><a href=".*?">(.*?)</a>.*?</p></td>')
# findaddres = re.compile(r'<td style="outline: 0px !important;">(.*?)</td>')
# findadress1 = re.compile(r'<td style="outline: 0px !important;"><a href=".*?">(.*?)</a></td>')
# 
# findlink = re.compile(r'<a href="(.*?)"')  # 创建正则表达式对象,表示规则(字符串的模式)
# =============================================================================

'''
通过findall找到所有table里面的tr
然后对tr里面的内容进行解析,如果没有链接,则data添加信息为空,有链接调用函数来解析链接网页
再向数据库传输解析内容
'''

def main():
    basicurl = "http://www.qianmu.org/ranking/1528.htm"
    datalist = getData(basicurl)
    #datalist = [[166,11,12,13],[188,22,23,24]]
    
    for data in datalist:
        print(data)
    saveDatadb(datalist,"rankData.db")


# 得到一个指定的网页内容
def askURL(url):
    et = html.etree
    respon = requests.get("http://www.qianmu.org/ranking/1528.htm")
    selector = et.HTML(respon.text)
    return selector

# 爬取主网页,将网页的tr提取出来进行分析
def getData(basicurl):
    datalist = []
    selector = askURL(basicurl)
    # 找出每个tr,对每个tr解析
    trs = selector.xpath('//div[@class="rankItem"]//tr[position()>1]')
    # names = selector.xpath('//div[@class="rankItem"]//tr[position()>1]/td/a/text() | //div[@class="rankItem"]//tr['
    #                        'position()>1]/td[2]/text()')
    # links = selector.xpath('//div[@class="rankItem"]//tr[position()>1]/td/a/@href')
    # 获得了每一个tr内容
    for tr in trs:
        data = []
        tr = html.tostring(tr, encoding='utf-8').decode('utf-8')
        name1 = re.findall(findNameData, tr)
        for tmp in range(len(name1)):
            name1[tmp] = cleanData(name1[tmp])
            print(name1[tmp])
        data.append(name1[1])
        data.append(name1[2])    
        data.append(name1[3])
        data.append(name1[0])
        datalist.append(data)

    return datalist

# 清洗数据,去除<>及中间内容,将"替换为'
def cleanData(basename):
    if not basename:
        return

    while ( "<" in basename):
        s_index = basename.index("<")
        e_index = basename.index(">")
        rm_str = basename[s_index:e_index+1]
        basename = basename.replace(rm_str,"")
    while ( "\"" in basename):
        basename = basename.replace('\"','\'')

    return basename

# 保存数据
def saveDatadb(datalist, dbpath):
    init_db(dbpath)
    conn = sqlite3.connect(dbpath)
    cur = conn.cursor()  # 获取游标
    # print("我执行了")
    for data in datalist:
        for index in range(len(data)):
            data[index] = '"' + str(data[index]) + '"'  # '"'+data[index]+'"'
        sql = '''
            insert into rankData(
            name, ename, address, rank) 
            values (%s)''' % ",".join(data)

        print(sql)
        cur.execute(sql)
        conn.commit()  # 提交
    cur.close()
    conn.close()  # 关闭链接

# 创建数据库
def init_db(dbpath):
    #创建表之前判断不存在才创建,存在则跳过
    sql = '''
        create table rankData(
        id integer primary key autoincrement,
        name text ,
        ename text ,
        address text ,
        rank text
        );
    '''

    conn = sqlite3.connect(dbpath)  # 建表
    cursor = conn.cursor()  # 游标
    cursor.execute(sql)  # 执行sql语句建表
    conn.commit()  # 提交
    conn.close()  # 关闭

if __name__ == "__main__":  # 当程序执行时,调用函数  这样写的目的是严格控制函数执行的主流程
    main()


4.上述程序使用的sqlite数据库,无需单独配置。

完整代码如上,本次实验对应的db文件以及数据库软件,已上传,设置的0积分,如果需要自行下载。


https://download.csdn.net/download/zhangb98/87364130



版权声明:本文为zhangb98原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。