微信好友分析
基于 Python 对微信好友进行数据分析,这里选择的维度主要有:性别、头像、签名、位置,主要采用图表和词云两种形式来呈现结果,其中,对文本类信息会采用词频分析和情感分析两种方法。在正式开始这篇文章前,简单介绍下本文中使用到的第三方模块:
image
当然在学习Python的道路上肯定会困难,没有好的学习资料,怎么去学习呢? 学习Python中有不明白推荐加入交流群号:973783996 群里有志同道合的小伙伴,互帮互助, 群里有不错的视频学习教程和PDF!
- itchat:微信网页版接口封装Python版本,在本文中用以获取微信好友信息。
- jieba:结巴分词的 Python 版本,在本文中用以对文本信息进行分词处理。
- matplotlib: Python 中图表绘制模块,在本文中用以绘制柱形图和饼图
- snownlp:一个 Python 中的中文分词模块,在本文中用以对文本信息进行情感判断。
- PIL: Python 中的图像处理模块,在本文中用以对图片进行处理。
- numpy: Python中 的数值计算模块,在本文中配合 wordcloud 模块使用。
- wordcloud: Python 中的词云模块,在本文中用以绘制词云图片。
- BDP: 可视化数据分析工具
# 首先导入用到的第三方模块
import itchat
import numpy as np
import os
from collections import Counter
import matplotlib.pyplot as plt
plt.rcParams['font.sans-serif']=['SimHei']#绘图时可以显示中文
plt.rcParams['axes.unicode_minus']=False#绘图时可以显示中文
from wordcloud import WordCloud,STOPWORDS,ImageColorGenerator
from PIL import Image
import math
import re
import snownlp
import jieba
import jieba.analyse
import pandas as pd
分析微信好友数据的前提是获得好友信息,通过使用 itchat 这个模块
itchat.auto_login(hotReload=True)
friends = itchat.get_friends(update=True)
同平时登录网页版微信一样,我们使用手机扫描二维码就可以登录,这里返回的friends对象是一个集合
好友性别
分析好友性别,我们首先要获得所有好友的性别信息,这里我们将每一个好友信息的Sex字段提取出来,然后分别统计出男、女 和保密的数目,我们将这三个数值组装到一个列表中,即可使用matplotlib模块绘制出饼图来,其代码实现如下:
def fun_analyse_sex(friends):
# 性别分析
sexs = list(map(lambda x:x['Sex'],friends[1:]))#收集性别数据
counts = list(map(lambda x:x[1],Counter(sexs).items()))#统计不同性别的数量
counts = sorted(counts)
labels = ['保密','男','女']#2:女,1:男,0:保密
colors = ['red','yellow','blue']
plt.figure(figsize=(20,8), dpi=80)
plt.axes(aspect=1)
plt.pie(counts, #性别统计结果
labels=labels, #性别展示标签
colors=colors, #饼图区域配色
labeldistance = 1.1, #标签距离圆点距离
autopct = '%3.1f%%', #饼图区域文本格式
shadow = False, #饼图是否显示阴影
startangle = 90, #饼图起始角度
pctdistance = 0.6 #饼图区域文本距离圆点距离
)
plt.legend(loc='upper left')#标签位置
plt.title(u'%s的微信好友性别比例' % friends[0]['NickName'])
plt.show()
- 结果如下:
生成头像
头像分析有两部分,(1)保存好友头像;(2)用所有好友头像生产一张图片
- 下载好友头像
通过用户名找到对应每个好友的头像,写入
HeadImages
目录中
def get_HeadImage(friends):
# 保存好友头像
if "HeadImages" not in os.listdir():
os.mkdir('HeadImages')
os.chdir("HeadImages")
for friend in friends:
img = itchat.get_head_img(userName=friend["UserName"])
with open(friend['UserName'].replace('|', '') + '.jpg', "wb") as f:
print("正在下载%s.jpg" % friend["NickName"])
f.write(img)
- 生产图片
使用PIL模块的Image方法,生成一张图片,再把每一张好友头像缩小贴到这张图片上
def all_head_images():
# 把所以好友头像生成一张图片
x = 0
y = 0
images = os.listdir("HeadImages")
print(len(images))
new_image = Image.new('RGBA', (640, 640))
# width = int(math.sqrt(640*640 / len(images)))
# line_num = int(640 / width)
line_num = int(math.sqrt(len(images)))
width = int(640/line_num)
for i in images:
image = Image.open('HeadImages/' + i)
image = image.resize((width, width), Image.ANTIALIAS)
new_image.paste(image, (x*width, y*width))
x += 1
if x == line_num:
x = 0
y += 1
new_image.save('all.png')
- 效果
好友签名分析
好友签名分析,也分为两部分:(1)切词构造词云;(2)文本分析,生活态度
- 构造词云
def fun_analyse_Signature(friends):
# 个性签名分析
signatures = ''
emotions = []
for friend in friends:
signature = friend['Signature']
if signature != None:
signature = signature.strip().replace("span","").replace("class","").replace("emoji","")#去除无关数据
signature = re.sub(r'1f(\d.+)',"",signature)
if len(signature) > 0:
nlp = snownlp.SnowNLP(signature)
emotions.append(nlp.sentiments)#nlp.sentiments:权值
signatures += " ".join(jieba.analyse.extract_tags(signature,5))#关键字提取
back_coloring = np.array(Image.open("xiaohuangya.jpg"))#图片可替换
word_cloud2 = WordCloud(font_path = 'simkai.ttf',
background_color = 'white',
max_words = 1200,
mask = back_coloring,
margin = 15)
word_cloud2.generate(signatures)
image_colors = ImageColorGenerator(back_coloring)
plt.figure(figsize=(20, 8),dpi=160)
plt.imshow(word_cloud2.recolor(color_func=image_colors))
plt.axis("off")
plt.show()
word_cloud2.to_file("signatures.jpg")
#人生观
count_positive = len(list(filter(lambda x:x>0.66,emotions)))#大于0.66为积极
count_negative = len(list(filter(lambda x:x<0.33,emotions)))#小于0.33为消极
count_neutral = len(list(filter(lambda x:x>=0.33 and x <= 0.66,emotions)))
labels = [u'积极',u'中性',u'消极']
values =(count_positive,count_neutral,count_negative)
plt.rcParams['font.sans-serif'] = ['simHei']
plt.rcParams['axes.unicode_minus'] = False
plt.xlabel("情感判断")
plt.ylabel("频数")
plt.xticks(range(3),labels)
plt.legend(loc='upper right')
plt.bar(range(3),values,color='rgb')
plt.title(u'%s的微信好友签名信息情感分析情况' % friends[0]['NickName'])
plt.show()
- 结果
好友位置
将姓名、省份写入csv文件
def analyseLocation(friends):
# 定义数据头
headers = ['NickName','Province']
with open('location.csv','w',encoding='utf-8',newline='',) as csvFile:
# DictWriter以字典的形式写入内容
# 设置写入格式
writer = csv.DictWriter(csvFile, headers)
# writeheader()实现添加文件头(数据名)
writer.writeheader()
for friend in friends[1:]:
# 定义一个字典
row = {}
# 按属性写入
row['NickName'] = friend['NickName']
row['Province'] = friend['Province']
# 将每个字典写入为一行
writer.writerow(row)
网友评论