一个超强的python案例,瞬间读懂爬虫与数据分析!

版权声明:禁止转载至其它平台,转载至博客需带上此文链接。 https://blog.csdn.net/qq_41841569/article/details/88572110

菜鸟一枚,所学的东西不多,记性也不好,因此对我来说巩固和实践很重要。这里简单的以爬取某电商网站某电脑品牌评论数据为例,简单回顾了爬虫python的写过程,可视化分析,以及介绍了文本关键字抽取。

学习Python中有不明白推荐加入交流群
号:984632579
群里有志同道合的小伙伴,互帮互助,
群里有不错的视频学习教程和PDF!

全文以代码和分析的形式展现具体的过程:

步骤:

1.网站的简单分析:爬取特定网页内容时,我们必须要找到其正确的

URL,并可以从中找到对应的规律。由于现有的电商网站评论信息都通过JS加载,因此商品详情页中并不会存在评论的具体信息。因此我们首先借助谷歌浏览器开发者工具进行查找:

a.具体方法是在商品详情页(请参考图2-1)点击鼠标右键,选择检查(请参考图2-2),在弹出的开发者工具界面(可参考图16-3)中选择Network,设置为禁用缓存(Disable cache)和只查看JS文件;

b.然后刷新页面。页面加载完成后向下滚动鼠标找到商品评价部分,等商品评价信息显示出来后,在下面Network界面的左侧筛选框中输入productPageComments,这时下面的加载记录中只有一条信息,这里包含的就是商品详情页的商品评论信息。点击这条信息,在右侧的Preview界面中可以看到其中包含了当前页面中的评论信息。

一个超强的python案例,瞬间读懂爬虫与数据分析!

一个超强的python案例,瞬间读懂爬虫与数据分析!

2.根据1中的简单分析,我们已经得到评论信息的URL:

  •  
https://sclub.jd.com/comment/productPageComments.action?callback=
fetchJSON_comment98vv12892&productId=8674557&score=0&sortType=5&
page=0&pageSize=10&isShadowSku=0&fold=1

仔细观察这条url可以发现,pageSize=10是页码。如果我们想要获取这个商品所有的评论,只需改变pageSize的值即可。

3.接下来开始爬虫的编写工作。2中已经分析了url,我们只获取一个商品的评论,因此id值不需要改变;为了获取更多该商品的评论,我们需要将pageSize在程序中作为一个变量,动态的获取多页的评论数据;由于只是进行简单的练习,pageSize在0到40变化。

程序主要分为三大部分:

part1 爬虫部分(数据下载函数,html转dataframe部分,数据清洗部分):

  •  
#导入必要的库
import sys
sys.path.append('d:/anocoda/envs/py3_cpu/libsite-packages/')
import requests
#请求和页面抓取)
import time
import random
import re
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import jieba
from datetime import datetime
  •  
#配置表头信息
header = {'User-Agent':'Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/58.0.3029.110 Safari/537.36',
 'Accept':'text/html;q=0.9,*/*;q=0.8',
 'Accept-Charset':'ISO-8859-1,utf-8;q=0.7,*;q=0.3',
 'Connection':'close',
 'Referer':'https://item.jd.com/10809260821.html'
 }
cookie = {'TrackID':'1mJoJegxxximdOIuMj1L78NM9IEUYBloQE8lNf5Kr0SN4bLXqWbNQGsuWLT7VSxXgBrnuOwGj9xdFUbqz1sLwrpxkzkjTA-HSsgVP9iJhv-g',
 '__jda':'122270672.413567069.1502329865.1505359716.1505377343.17',
 '__jdb':'122270672.4.413567069|17.1505377343',
 '__jdc':'122270672',
 '__jdu':'413567069',
 '__jdv':'122270672|p.egou.com|t_36378_879430_c|tuiguang|5191ffe38de346c28750ae3309faf11a|1505288084897',
 'areaId':'2',
 'cn':'17',
 'ipLoc-djd':'2-2830-51811-0.137557061',
 'ipLocation':'%u4E0A%u6D77',
 'mx':'0_X',
 'rkv':'V0800',
 'user-key':'acce01e8-1533-4aaa-bcea-34ac9b6d6a53',
 'xtest':'4657.553.d9798cdf31c02d86b8b81cc119d94836.b7a782741f667201b54880c925faec4b'}

上述部分主要是导入必要的python库,以及初始化表头信息部分(这样做的目的是伪装术,把自己伪装成浏览器,防止被服务端封掉IP);

  •  
#网页下载器
def downloadPage(url1,url2):
 ran_num = random.sample(range(40),40)
 a = ran_num[0]
 for i in ran_num:
 url = url1 + str(i) + url2
 r = requests.get(url, headers=header, cookies=cookie)
 if i==a:
 html1 = r.content
 else:
 html2 = r.content
 html1 = html1+html2
 time.sleep(10)
 print('当前抓取页面:',url,'状态:',r)
 html = str(html1,encoding='gbk')
 file = open('./spiner_jd.txt','w')
 file.write(html)
 file.close()

爬取每一页的评论数据,并将这些数据拼接和编码存到txt文件中,后面的数据处理直接操作txt文件中的数据;

  •  
# html->dataframe 通过正则表达式处理数据
def dataProcess():
 html = open('./spiner_jd.txt','r').read()
 #使用正则表达式提取结构化信息
 #1.content评论信息
 #2.createTime 评论时间
 #3.isMobile 客户端类型
 #4.productColor 产品介绍
 #5.userLevelName 用户级别
 #6.nickName 用户名称
 # 使用正则提取userClient字段信息
 content = re.findall(r'"id":d*?,"guid".*?,"content":(.*?),',html)
 createTime = re.findall(r'"id":d*?,"guid".*?,"creationTime":(.*?),"isTop":.*?,',html)
 # isMobile = re.findall(r'"id":d*?,"guid".*?,"userClientShow":.*?","isMobile":(.*?)}',html)
 productColor = re.findall(r'"discussionId":.*?,"productColor":(.*?),',html)
 userLevelName = re.findall(r'"anonymousFlag".*?,"userLevelName":(.*?),',html)
 # nickName = re.findall(r'"isReplyGrade":.*?,"nickname":(.*?),',html)
 print('content_len:',len(content),';time_len:',len(createTime),';productColor:',len(productColor),
 ':userLevelName:',len(userLevelName))
 df = pd.DataFrame({'content':content,'createTime':createTime,'productColor':productColor,
 'userLevelName':userLevelName})
 df.to_csv('./spiner_df.csv',index=None)
  •  
 df = pd.read_csv('./spiner_df.csv')
 df = df.applymap(lambda x:re.sub('"','',x))
 #这里使用局部替换法进行了双引号的去除 df['createTime'] = df['createTime'].map(lambda x:datetime.strptime(x,'%Y-%m-%d %H:%M:%S'))
 #使用datetime中的strptime将字符串转为了时间
 df.head()
 df['createTime'] = df['createTime'].map(lambda x:datetime.strptime(x,'%Y-%m-%d %H:%M:%S'))
 #使用datetime中的strptime将字符串转为了时间
 df['year'] = df['createTime'].map(lambda x:x.year)
 df['month'] = df['createTime'].map(lambda x:x.month)
 df['day'] = df['createTime'].map(lambda x:x.day)
 df['hour'] = df['createTime'].map(lambda x:x.hour)
 df.head()

一个超强的python案例,瞬间读懂爬虫与数据分析!

读取txt文件中的数据,并通过正则化表达式获得对应含义的数据,将获得的数据以字典的形式化初始化成DataFrame格式(这样做的目的是,DataFrame格式的数据更容易用来分析和可视化);

part2 可视化分析部分:

  •  
#可视化分析
#1.获取年——月 对应的评论数量
plt.rcParams['font.sans-serif']=['SimHei'] ###显示中文
plt.rcParams['axes.unicode_minus']=False ##防止坐标轴上的-号变为方块
con_count = df.groupby(['year','month'])['content'].count()
#2018.8-2019.2月
x = np.array(range(7))
plt.figure(figsize=(10,4),dpi=90)
plt.bar(x,con_count.values,color='#99CC01')
plt.title('分月评论数量变化趋势')
plt.xlabel('月份')
plt.ylabel('数量')
labels = ['2018-8','2018-9','2018-10','2018-11','2018-12','2019-1','2019-2']
plt.grid(color='#95a5a6',linestyle='--',axis='y')
plt.xticks(x,labels)
plt.show()

一个超强的python案例,瞬间读懂爬虫与数据分析!

首先通过groupby获取对应月份的评论数量,然后借matplotlib.pyplot库构建了一个直方图,对月份评论数量变化趋势进行可视化。

  •  
#用户购买会员分布情况查看
client_count = df.groupby(['userLevelName'])['content'].count()
plt.figure(figsize=(10,4),dpi=90)
x = np.array(range(client_count.shape[0]))
plt.bar(x,client_count,color='#99CC01')
plt.xlabel('会员类型')
plt.ylabel('数量')
labels = ['PLUS会员','PLUS会员(试用)','企业会员','注册会员','金牌会员','砖石会员','铜牌会员','银牌会员']
plt.title('购买会员分布情况')
plt.grid(color='#95a5a6',linestyle='--',axis='y')
plt.grid()
plt.xticks(x,labels)
plt.show()

一个超强的python案例,瞬间读懂爬虫与数据分析!

part3 关键字抽取部分:

  •  
#评论语义分析,前20关键字抽取
content_str = ' '.join(df['content'].values)
stop_word = ['div','class','jpg','jfs','shaidan','buyimg','com','http','src','uploading','img','uploadimgdiv','uploadimg','border','img30.360']
f = open('./stop_word.txt','w')
for i in stop_word:
 f.write(i)
 f.write('
')
f.close()
import jieba.analyse
word_rank = jieba.analyse.extract_tags(content_str, topK=20, withWeight=True, allowPOS=(),)
jieba.analyse.set_stop_words('./stop_word.txt')
#转化为dataframe
word_rank = pd.DataFrame(word_rank,columns=['word','rank'])
#查看关键词及权重
word_rank.sort_values(by='rank',ascending=False)

一个超强的python案例,瞬间读懂爬虫与数据分析!

这里运用中文分词工具jieba库中的jieba.analyse抽取了爬取的评论数据中排名前20的词汇;需要注意的是由于爬取的评论信息中可能混有html标签,在抽取关键字时会影响正确的排名顺序;为此,首先将可能出现的html标签构造为一个停用词表,并在抽取关键字之前,通jieba.analyse.s-et_stop_words(path)函数引入停用词;最终我们获得了比较合理的排名前20的关键字。

猜你喜欢

转载自blog.csdn.net/qq_41841569/article/details/88572110