账号检测
先去https://wx.qq.com/,测试自己的账号能否登陆微信网页版,要是能登陆,跟着往下步骤走,就可以进行爬虫了,否则,那就做不了数据分析了,不用跟着步骤走了,出门左拐,嘻嘻
若出现下图报错
这个是腾讯的问题,较新的微信,会禁止网页版登陆,因此用不了python第三方库itchat,如果你的微信号比较新,那会出现以下报错
需要用到的库
import re
import os
import itchat
import math
import jieba
import pyecharts
import wordcloud
import PIL
import matplotlib.pyplot as plt
如果,那个库报错的话,就在cmd上或者Terminal上安装,直达没有报错为止
pip install re
pip install os
pip install itchat
pip install math
pip install jieba
pip install pyecharts
pip install wordcloud
pip install PIL
pip install matplotlib
效果图展示
1: 男女性别比例
作为一个理工科男生,我太难了
获取好友性别信息
# 获取好友性别信息
friends = itchat.get_friends(update=True) # 获取微信所有好友全部信息
total = len(friends) # 统计微信好友数量
man = woman = other = 0 # 性别初始化
for fri_info in friends:
sex = fri_info['Sex'] # sex=1 代表男性 sex=2代表女性
if sex == 1:
man += 1
elif sex == 2:
woman += 1
else:
other += 1
print("微信好友总数{},男性:{}人,女性:{}人,未设置性别:{}人".format(total, man, woman, other))
运行效果
2: 所在省份分布
我的好友大部分都是广东的,小林同学也是个广东人哈
3: 所在城市分布
肇庆的路过一下
获取省份省份、城市信息
# 获取所在省份和城市
friends = itchat.get_friends(update=True) # 获取微信所有好友全部信息
prov_dict, city_dict = {}, {} # 省份,城市初始化
for fri_info in friends:
prov = fri_info['Province'] #字典中,Pprovince对应着省份
city = fri_info['City'] #字典中,City对应着城市
if prov and prov not in prov_dict.keys(): #如果省份键值不在里面,新增省份
prov_dict[prov] = 1
elif prov: #反之加1
prov_dict[prov] += 1
if city and city not in city_dict.keys():
city_dict[city] = 1
elif city:
city_dict[city] += 1
print(prov_dict)
print()
print(city_dict)
运行效果
4: 个性签名词云图
收集好友的个性签名,做词云图,努力位于榜首,因此也看得出来,我的好友多数是贴上奋斗者标签
获取个性签名信息
# 获取个性签名
friends = itchat.get_friends(update=True) # 获取微信所有好友全部信息
rule = re.compile("1f\d+\w*|[<>/=]") # 定义正则规则
sign_li = [] # 存放微信好友_个性化签名
for fri_info in friends:
signature = fri_info['Signature'] #字典中,Signature对应着个性签名
if signature:
#去除不规范的字符......
sign_deal = signature.replace('\n', '').replace('\t', '').replace(' ', '') \
.replace("span", "").replace("class", "").replace("emoji", "")
sign = rule.sub("", sign_deal)
sign_li.append(sign)
for i in sign_li:
print(i,end=" ")
运行效果
5:微信好友头像拼接图
获取好友头像
# 获取好友头像
friends = itchat.get_friends(update=True) # 获取微信所有好友全部信息
num = 1 # 图片命名初始化
photos = "d:\\wxFriends\\photos"
if not os.path.exists(photos):
os.makedirs(photos) # 创建多级目录,指定存放文件路径
path = "d:\\wxFriends"
for fri_info in friends:
img = itchat.get_head_img(userName=fri_info["UserName"])
file_image = open(photos + "/" + str(num) + ".jpg", 'wb')
file_image.write(img)
file_image.close()
num += 1
运行效果,图片在D:\wxFriends\photos下
源代码汇总
数据保存在D:\wxFriends文件夹下
注意在处理词云的时候,背景图片的路径问题,跟py放同一个文件夹,当然路径也可以改
import re
import os
import itchat
import math
import jieba
import pyecharts
import wordcloud
import PIL
import matplotlib.pyplot as plt
itchat.auto_login(hotReload=True)
print("正在分析数据,请稍等一会儿")
print("正在分析数据,请稍等一会儿")
print("正在分析数据,请稍等一会儿")
def wxFriends():
friends = itchat.get_friends(update=True) # 获取微信所有好友全部信息
total=len(friends) #统计微信好友数量
#初始化
man = woman = other = 0 #性别初始化
prov_dict,city_dict = {},{} #省份,城市初始化
plt.rcParams['font.sans-serif'] = ['SimHei'] # 设置rc参数显示中文标题,字体为SimHei
plt.rcParams['axes.unicode_minus'] = False # 用来正常显示字符
sign_li = [] # 存放微信好友_个性化签名
num = 1 #图片命名初始化
photos="d:\\wxFriends\\photos"
if not os.path.exists(photos):
os.makedirs(photos) #创建多级目录,存放文件
path="d:\\wxFriends"
for fri_info in friends:
# 统计性别
sex=fri_info['Sex'] #sex=1 代表男性 sex=2代表女性
if sex==1:
man+=1
elif sex==2:
woman+=1
else:
other+=1
# 获取所在省份和城市
prov = fri_info['Province']
city = fri_info['City']
if prov and prov not in prov_dict.keys():
prov_dict[prov] = 1
elif prov:
prov_dict[prov] += 1
if city and city not in city_dict.keys():
city_dict[city] = 1
elif city:
city_dict[city] += 1
# 获取个性签名词云
rule = re.compile("1f\d+\w*|[<>/=]") # 定义正则规则
signature = fri_info['Signature']
if signature:
sign_deal = signature.replace('\n', '').replace('\t', '').replace(' ', '') \
.replace("span", "").replace("class", "").replace("emoji", "")
sign = rule.sub("", sign_deal)
sign_li.append(sign)
#获取好友头像图片
img = itchat.get_head_img(userName=fri_info["UserName"])
file_image = open(photos + "/" + str(num) + ".jpg", 'wb')
file_image.write(img)
file_image.close()
num += 1
# 区域Top10
prov_dict_top10 = sorted(prov_dict.items(), key=lambda x: x[1], reverse=True)[0:10]
# 城市Top10
city_dict_top10 = sorted(city_dict.items(), key=lambda y: y[1], reverse=True)[0:10]
#画省份
provice = list(prov_dict.keys())
values = list(prov_dict.values())
map = pyecharts.Map("微信好友_省份分布", width=1100, height=500)
map.add("", provice, values, visual_range=[0, 500], maptype='china', is_visualmap=True,
visual_text_color='#000', is_label_show=True)
map.render(path+"/微信好友_省份分布.html")
#画城市
city_nm, city_num = [], [] # 城市 + 数量
for city_data in city_dict_top10:
city_nm.append(city_data[0])
city_num.append(city_data[1])
colors = ['#ff105c', '#ff8352', '#ffb399', '#fcff2e', '#fff569',
'#5aff02', '#9bff6c', '#25a1ff', '#8bcdff', '#dea4ff']
index = range(len(city_num))
#柱状图bar
plt.bar(index, city_num, color=colors, width=0.5, align='center')
plt.xticks(range(len(city_nm)), city_nm) # 横坐轴标签
for x, y in enumerate(city_num):
#在柱子上方1.2处标注值
plt.text(x, y + 1.2, '%s' % y, ha='center', fontsize=10)
plt.ylabel('城市好友人数') # 设置纵坐标标签
plt.title('微信好友_城市Top10') # 设置标题
plt.savefig(path + '/微信好友_城市Top10') # 保存图片
# 画性别比例
man_ratio = man / total * 100
woman_ratio = woman / total * 100
other_ratio = other / total * 100
plt.figure(figsize=(5, 5)) # 绘制的图片为正圆
sex_li = ['男', '女', '未设置性别']
radius = [0.01, 0.01, 0.01] # 设定各项距离圆心n个半径
colors = ['red', 'yellowgreen', 'lightskyblue']
proportion = [man_ratio, woman_ratio, other_ratio]
plt.pie(proportion, explode=radius, labels=sex_li, colors=colors, autopct='%.2f%%') # 绘制饼图
# 加入图例 loc = 'upper right' 位于右上角 bbox_to_anchor=[0.5, 0.5] # 外边距 上边 右边 borderaxespad = 0.3图例的内边距
plt.legend(loc="upper right", fontsize=10, bbox_to_anchor=(1.1, 1.1), borderaxespad=0.3)
# 绘制标题
plt.title('%d个好友_性别比例' % total)
# 保存图片
plt.savefig(path + '/微信好友_性别比例')
#画词云
comment_txt = ''
back_img = plt.imread('pikaqiu.jpg')
cloud = wordcloud.WordCloud(font_path=path + '/simhei.ttf', # 若是有中文的话,这句代码必须添加,不然会出现方框,不出现汉字
background_color="white", # 背景颜色
max_words=5000, # 词云显示的最大词数
mask=back_img, # 设置背景图片
max_font_size=100, # 字体最大值
random_state=42,
width=800, height=755, margin=2, # 设置图片默认的大小,但是如果使用背景图片的话,保存的图片大小将会按照其大小保存,margin为词语边缘距离
)
for li in sign_li:
comment_txt += ' '.join(jieba.cut(li, cut_all=False))
wc = cloud.generate(comment_txt)
image_colors = wordcloud.ImageColorGenerator(back_img)
plt.imshow(wc.recolor(color_func=image_colors))
wc.to_file(path+'/微信好友_个性签名词云图.png')
# #收集图片
ls = os.listdir(photos)
each_size = int(math.sqrt(float(640 * 640) / len(ls))) # 算出每张图片的大小多少合适
lines = int(640 / each_size)
image = PIL.Image.new('RGBA', (640, 640)) # 创建640*640px的大图
x = 0
y = 0
#对所有图像进行拼接
for i in range(0, len(ls) + 1):
try:
img = PIL.Image.open(photos + "/" + str(i) + ".jpg")
except IOError:
print("Error")
else:
img = img.resize((each_size, each_size), PIL.Image.ANTIALIAS)
image.paste(img, (x * each_size, y * each_size)) # 粘贴位置
x += 1
if x == lines: # 换行
x = 0
y += 1
image.save(path + "/微信好友_头像拼接图.png")
print("数据已经分析完成,文件在D:\wxFriends下")
while True:
a = input("按任意键结束")
break
if __name__=="__main__":
wxFriends()