栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Python

【Python Selenium应用】知网引证文献翻页采集(简单方便)

Python 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

【Python Selenium应用】知网引证文献翻页采集(简单方便)

学妹需要查询一批文献的引证文献数据,采集指定文章的引证文献数据

采集思路

学妹提供的数据为题名+作者。

在高级检索界面输入主题及作者,拿到文章链接以及引证文献列表链接。为避免被参数困扰,数量不多的情况就直接使用selenium。若出现多条返回结果,则可以在筛选框筛选出显示50条及按相关度排序,这样基本上在第一页就可以拿到相应数据,无需翻页。

拿到引证文献列表链接后开始采集每篇引证文献的链接。期刊、博士等每个类目下都有分页,每页10条。此时selenium最为简单方便。
具体思路如下:
先解析出期刊等每个类目的标签(‘div[@class=“essayBox”]’);
再遍历每个essayBox标签,解析出数量;
若数量小于10条,直接解析即可;
若大于10条,先解析再翻页,直到翻到最后一页。

拿到引证文献的链接,就可以愉快的采集相应文献的数据了!

代码

引入相关包

# -*- coding: utf_8 -*-
import os
import time
import random
import pandas as pd
from lxml import etree
from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.chrome.options import Options

设置远程调试

options = Options()
options.debugger_address = "127.0.0.1:9299" 
browser = webdriver.Chrome(chrome_options=options)

手动启动浏览器
CMD: 浏览器路径 + --remote-debugging-port=9299

def get_data_list(essayBox_index):
    """
    :param essayBox_index: 分类标签的索引
    :return: 当前标签下所有文献标题及链接
    """
    data_list = []
    res = browser.page_source
    xpath_str = f'//div[@id="divResult"]/div[@][{essayBox_index}]'
    info = etree.HTML(res)
    data_list_info = info.xpath(xpath_str)[0]
    data_list_1 = [f"https://kns.cnki.net{i}" for i in data_list_info.xpath('./ul/li/a/@href')]
    data_list_2 = [i.strip() for i in data_list_info.xpath('./ul/li/a//text()')]
    for k, v in dict(zip(data_list_1, data_list_2)).items():
        dict_ = {'yw_title': v, 'yw_link': k}
        data_list.append(dict_)
    return data_list

def get_page_info(essayBox_index):
    """
    :param essayBox_index: 分类标签的索引
    :return: 当前标签下页码信息
    """
    res = browser.page_source
    xpath_str = f'//div[@id="divResult"]/div[@][{essayBox_index}]/div[@]//text()'
    info = etree.HTML(res)
    page_info = ''.join([i.strip() for i in info.xpath(xpath_str) if i.strip() != ''])
    return page_info

def click_next_page(essayBox_index):
    """
    :param essayBox_index: 分类标签的索引
    :return: 点击当前标签内下一页
    """
    next_page = browser.find_elements(By.XPATH, f'//div[@][{essayBox_index}]//div[@]/span[1]/a')[-2]
    print('next_page: ', next_page)
    browser.execute_script("$(arguments[0]).click()", next_page)

def run(FileName, quote_link):
    print('正在采集:', FileName)
    browser.get(quote_link) 
    time.sleep(random.randint(3, 5))  # 加载较慢,这里一定要等待2秒左右,保险起见我等待3-5秒
    res = browser.page_source
    info = etree.HTML(res)
    essayBox_labels = info.xpath('//div[@id="divResult"]/div[@]')  # 获取每个文献分类标签
    data_list_all = []
    for essayBox_label in essayBox_labels:
        data_type = ''.join([i.strip() for i in essayBox_label.xpath('./div[@]/text()') if i.strip() != ''])
        data_num = int(''.join([i.strip() for i in essayBox_label.xpath('./div[@]//span[@name="pcount"]/text()') if i.strip() != '']))  # 该分类下文献的数量
        essayBox_index = essayBox_labels.index(essayBox_label) + 1  # 该分类标签索引,xpath里面从1开始所以+1
        if data_num <= 10:  # 文献数量<=10无需翻页,直接解析即可
            print(essayBox_label, data_type, data_num)
            data_list = get_data_list(essayBox_index=essayBox_index)
            for ij in data_list:
                ij.update({'data_type': data_type, 'data_num': data_num})
                ij.update(item_1)
                print(ij)
                data_list_all.append(ij)
        else:  # 文献数量>10,在while True里面循环 解析+翻页
            print(essayBox_label, data_type, data_num)
            while True:
                data_list = get_data_list(essayBox_index=essayBox_index)  # 解析文献名称及链接
                for ij in data_list:
                    ij.update({'data_type': data_type, 'data_num': data_num})
                    ij.update(item_1)
                    print(ij)
                    data_list_all.append(ij)
                page_info = get_page_info(essayBox_index=essayBox_index)  # 获取当前页码标签内是否有下一页
                if '下一页' in page_info:
                    click_next_page(essayBox_index=essayBox_index)  # 如果有下一页就点击
                else:
                    break
                time.sleep(random.randint(2, 3))
    # 懒得入数据库,直接保存在本地,每条数据一个文件,全部采集完成后pd.concat直接合并即可
    file_path = f"./rd_3/{FileName}.xlsx"
    df_2 = pd.Dataframe(data_list_all)
    df_2.to_excel(file_path, index=False)
    print('文件保存成功:', file_path)
    time.sleep(random.randint(2, 3))

if __name__ == '__main__':
    # 读取文件
    df_1 = pd.read_excel('./20211210.xlsx')
    list_1 = df_1.to_dict(orient='records')
    list_jd = [i.replace('.xlsx', '') for i in os.listdir('./rd_3')]
    # 文件我是保存在本地rd_3文件夹下面的,跑之前读一遍已经采集的FileName
    for item_1 in list_1:
        FileName = item_1['FileName']
        quote_link = item_1['引用链接']
        if FileName in list_jd:
            print('文件已采集:', FileName)
            pass
        else:
            if quote_link == quote_link:
                run(FileName=FileName, quote_link=quote_link)

运行结果:

以上代码为翻页采集列表,至于采集引用链接及文献详情就不再赘述。

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/657163.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号