267019條貓眼數據加持,原來你是這樣的《流浪地球》——python數據分析全流程代碼實現!

2019年春節檔,《流浪地球》橫空出世,在強勢口碑加持下,上映兩週多票房即突破40億! 與之相隨的主題也霸佔了春節期間的話題榜。 作爲一部現象級的電影,筆者也很感興趣,特意爬取了2月5日(初一)至2月12日(初八) 267019條貓眼影評,多角度可視化分析了《流浪地球》的數據規律。 接下來,跟我看看這267019人究竟說了什麼吧!

數據分析準備工作

  • 整個數據分析分爲數據爬取、數據清洗、數據可視化和文本分析四個板塊
  • 項目採用Anaconda環境,過程仍需安裝多個第三方模塊

所需第三方模塊(需提前安裝)

  • 數據可視化:pyecharts(是一個用於生成 Echarts 圖表的類庫).
  • 文本分析:jieba(中文分詞),wordcloud(生成詞雲)等

(一)數據爬取階段

1、工具庫準備(備用模塊:time,random,datetime,requests,json)

2、備用user-agents(準備多個可用的user_agents,應用於爬蟲階段)

3、爬蟲封裝代碼(詳細的爬蟲實現代碼)

源代碼github地址:https://github.com/Willsgao/Personal-projects/

爬蟲階段總結

  • 1、爬取2019-02-05日——2019-02-12日,8天共267019條評價數據。
  • 2、實際爬取過程中會因爲網站的反扒機制多次中斷,導致部分數據丟失。

(二)數據清洗階段

  • 1、此階段主要依靠pandas對原始數據進行預處理
  • 2、爬蟲階段得到的數據分佈在多個csv文件中需要進行合併
  • 3、數據中存在空值,根據需求進行刪除或補充操作

1、導入數據清洗所需工具庫

import pandas as pd
import glob  # 在csv文件合併中讀取所有的csv文件

2、將爬取的多個csv文件進行合併

# 讀取爬取的所有csv文件
csv_files = glob.glob('./*.csv')

# 將csv文件進行合併
for file in csv_files:
    data = pd.read_csv(file, names=['暱稱','城市','評語','評分','日期','性別標籤'],
                       encoding='utf_8_sig',engine='python',header=None)
    data.to_csv('合併文件/流浪地球01_comments.csv', mode='a', 
                encoding='utf_8_sig', index=False, sep=',')

3、數據基本信息特徵

# 讀取合併後的文件信息
datas = pd.read_csv('合併文件/流浪地球01_comments.csv',
                encoding='utf_8_sig',engine='python')
# 查看數據的基本信息屬性
datas.describe()

在這裏插入圖片描述

4、所需的目標數據的預處理

# 統計各城市出現的數據信息
ct_datas = pd.DataFrame(datas['城市'])
# 將城市名稱爲空的數據刪除
ct_datas = ct_datas.dropna(axis=0)
print(ct_datas.size)

# pandas讀取會員的評分數據
df_score =  pd.DataFrame(datas['評分'])
# 將評分爲空的數據刪除
df_score = df_score.dropna(axis=0)
print(df_score.size)

# 讀取會員的評語數據
dt_coms = pd.DataFrame(datas['評語'])
# 將評語爲空的數據刪除
dt_coms = dt_coms.dropna(axis=0)
print(dt_coms.size)
# 將評語保存爲txt文檔
dt_coms.to_csv("流浪地球_影評.txt",
               sep='\t', index=False)

5、數據清洗小結

  • 主要根據數據分析的業務需求進行初步的數據處理
  • 更加細緻的數據處理在業務分析階段實現

(三)數據分佈可視化

  • 利用pyecharts可視化參與影評的粉絲分佈情況
  • 分別通過Geo和Bar函數進行數據可視化

1、指明文件編碼格式,識別中文字符

# 導入相關工具庫
import importlib
import sys
importlib.reload(sys)

2、城市分佈信息處理

  • 爲實現Geo可視化全國粉絲分佈,對ct_datas進行處理
  • 定義數據格式處理的相關函數
    ******* 詳細代碼見github源代碼******
# 城市信息列表化
# 將讀取的城市特徵信息轉化爲列表
def list_cities(ct_datas):
    pass
    return city_lists

# 城市列表字典化,將城市列表轉化爲鍵爲城市值爲人數的字典
def set_list_cities(city_lists):
    pass
    return city_sets

# Geo格式化,將城市字典轉化爲Geo所需的數據格式
# 將城市信息和評論數量以元組格式添加到列表中
def geo_city_infos(city_sets):
    pass
    return city_infos

# 將Geo格式化的列表重新轉化爲字典格式
def set_info_cities(city_infos):
    pass
    return city_sets
# 生成城市數據字典
city_sets = set_list_cities(city_lists)
print(len(city_sets))

# 生成格式化城市數據
city_infos = geo_city_infos(city_sets)
print(len(city_infos))
data = city_infos

3、Geo可視化粉絲分佈圖

  • pyecharts源代碼的數據庫中無法識別所有的城市,因此不能識別的城市需要特殊處理。
  • 方法一是將所有不能識別的城市數據刪除;
  • 方法二是在源代碼城市數據庫中添加新城市的經緯度值。
考慮到操作的簡便性,此處採用方法一,將不能識別的城市數據刪除
# Geo繪圖函數
def geo_picture(data, city_sets):
    # 導入相關工具庫
    # 導入Geo模塊進行城市數據分析
    from pyecharts import Geo
    
    useless_cities = []
    city_infos = []
    for i in range(len(data)):
        geo = Geo("《流浪地球》全國觀影粉絲分佈圖", "data from Maoyan", 
                  title_color="#fff",title_pos="center", width=1000,
                  height=750, background_color='#404a59')
        attr, value = geo.cast(data)

        try:
            geo.add("", attr, value, visual_range=[0, 200], maptype='china',type="effectScatter",
                    visual_text_color="#fff",symbol_size=10, is_visualmap=True)
        except Exception as e:
    #         print(e)
            # 在異常信息中提取無法被pyecharts識別的城市
            city = str(e).split()[-1]
            # 將不能識別的城市名稱收集到列表中
            useless_cities.append(city)
            # 剔除無法識別的城市信息
            city_sets.pop(city)
            city_infos = geo_city_infos(city_sets)
            data = city_infos
    #生成html文件
    geo.render("全國觀影粉絲分佈圖.html")
    return geo,city_infos,useless_cities


# 處理不能識別的城市名稱,重新參與畫圖
def handle_cities(filename, city_sets):
    # 讀取未識別的城市名稱
    ul_cities = []
    with open(filename,'r',encoding='utf_8') as f:
        ul_lists = f.readlines()
        
    # 刪除非中文格式的城市
    for city in ul_lists:
        ch = city.strip()[0]
        if u'\u4e00' <= ch <= u'\u9ffff':
            ul_cities.append(city.strip())
    print(len(ul_cities))
    
    # 判斷是否由於下面集合中的字的缺失或是多餘導致
    ad_re_cities = []
    cityname = ''
    lists = ['縣','區','市','州']
    for city in ul_cities:
        if city[-1] not in lists:
            for j in lists:
                cityname = city+j
                ad_re_cities.append((cityname,city_sets[city]))
        elif len(city)>=3:
            cityname = ''.join(city[:-1])
            ad_re_cities.append((cityname, city_sets[city]))
        else:
            continue
    return ad_re_cities


# 存儲不能識別的城市信息
def store_cities(useless_cities,filename):
    ul_cities = pd.DataFrame(useless_cities)
    ul_cities.to_csv(filename,sep='\t', index=False)
# 運行Geo模塊
pre_city_sets = set_list_cities(city_lists)
print(len(pre_city_sets))
geo,city_infos,useless_cities = geo_picture(data, pre_city_sets)

# 定義存儲不能識別城市的文件名稱
filename = '未識別城市.txt'

# 存儲城市信息
store_cities(useless_cities,filename)
# 生成處理後的新城市信息
print(len(city_sets))
ad_re_cities = handle_cities(filename, city_sets)

​​# 處理後的城市與已識別的城市信息合併
final_city_infos = ad_re_cities + city_infos
cur_city_sets = set_info_cities(final_city_infos)
# print(next_city_sets)

# 重新運行Geo模塊
geo,_,_ = geo_picture(final_city_infos,cur_city_sets)

# 繪製全國觀影粉絲分佈圖
# 直接在notebook中顯示
geo

在這裏插入圖片描述

Geo可視化粉絲分佈小結

  • pyecharts識別城市能力有限,導致380個左右的城市信息無法識別
  • 總體上來說主要城市信息是能正常識別的,因此不會對頭部信息有較大影響
  • 對於定型化了解全國影迷分佈仍具有很大的參考價值

具體分佈信息見上圖

  • 1、中東部是《流浪地球》影迷和影評的主力;
  • 2、廣大的西部地區影評人數嚴重不足;
  • 3、影評的密度與地區人口的分佈密度正相關。

4、利用Bar可視化評論頭部城市信息

  • 利用pyecharts中的Bar模塊進行分析
  • 查看影評數量在前20名的城市信息
  • 利用pyecharts中的Style模塊定義可視化圖形
from pyecharts import Bar
from pyecharts import Style

# 定義樣式
style = Style(
    title_color='#fff',
    title_pos='center',
    width=800,
    height=500,
    background_color='#404a59',
    subtitle_color='#fff'
)

# 根據城市數據生成柱狀圖
city_counts = ct_datas.groupby("城市").size()
city_sorted = city_counts.sort_values(ascending=False).head(20)

bar = Bar("《流浪地球》評星人來源排行TOP20", "蝸牛行天下", **style.init_style)
attr, value = bar.cast(list(city_sorted.items()))
bar.add("", attr, value, is_visualmap=True, visual_range=[0, 2500],
        visual_text_color='#fff', label_color='#fff',
        xaxis_label_textcolor='#fff', yaxis_label_textcolor='#fff', 
        is_more_utils=True,is_label_show=True)

# 保存可視化圖片文件
bar.render("評星人來源排行-柱狀圖.html")
# 圖像可視化
bar

在這裏插入圖片描述

Bar可視化分析小結

  • 從上圖可見,城市粉絲評論數量順序與城市的經濟實力排名相吻合。
  • 此外,城市粉絲評論數量順序也與城市人口數量排名正相關。
  • 由此可以初步推斷,城市經濟實力越強。人口越多,市民的觀影數量越多,娛樂生活越豐富。

5、Pie模塊可視化《流浪地球》的星級評價&區分性別

  • 利用pyecharts的Pie模塊分析《流浪地球》的評分分佈
  • 將評分進行分段處理,用一星到五星來標定影片評價等級
  • 分別考察不同性別影迷對《流浪地球》的評分結果,探究性別影響。
  • 性別缺失值較多,但因爲數據是否缺失沒有明顯的性別差異,缺失值可以刪除
# 構建Pie圖生成函數
def genPiePicture(df_score):
    pass   # 詳細代碼見文末github地址
    return pie

分性別處理影評數據

# 處理性別數據
# 1、刪除缺失值
gender_datas = datas.dropna(subset=['性別標籤'])
print(len(gender_datas))

# 2、分別讀取男女性別數據,男gender值爲'1.0',女爲'2.0'
male_datas = gender_datas[gender_datas.性別標籤=='1.0']
female_datas = gender_datas[gender_datas.性別標籤=='2.0']

# 3、分別讀取男女會員的評分數據
male_score =  pd.DataFrame(male_datas['評分'])
female_score =  pd.DataFrame(female_datas['評分'])
# 生成男性的評分pie圖
male_pie = genPiePicture(male_score)
male_pie
# 生成女性的評分pie圖
female_pie = genPiePicture(female_score)
female_pie
男性星級評價比例圖

在這裏插入圖片描述

女性星級評價比例圖

在這裏插入圖片描述

《流浪地球》星級評價小結

  • 男女影評者均有85%左右的比例對《流浪地球》給出了5星的評價。
  • 男女影評者具有超過93%的影評者對《流浪地球》給出了超過4星的評價。
  • 《流浪地球》是一部基本沒有性別區分度的影片,男女通喫。
  • 《流浪地球》是一部評價很高(評分數據超過大多數影片),值得一看。

(四)評語文本分析

  • 利用jieba分詞工具包對評語進行分詞處理,分析評語文本信息。
  • 對所得的評語分詞進行頭部分析,利用wordcloud生成詞雲,可視化評語。
  • 原始評語過於龐大(700萬字),此處不做詳細分析。
  • 更爲詳細的文本分析見‘《流浪地球》貓眼評語文本分析’一文。

1、導入文本分析工具包

import jieba
import matplotlib.pyplot as mp
from wordcloud import STOPWORDS, WordCloud
from os import path
from PIL import Image
import numpy as np

2、獲取樣本評語數據

  • 爲簡化分析,隨機選擇了一個小樣本(1.6萬字左右)進行簡要分析。
# 獲取所有的評論
comments = []

with open("流浪地球_影評01.txt", 'r', encoding='utf-8') as f:
    rows = f.readlines()
    for row in rows:
        try:
            comment = row.strip().split(',')
        except IndexError:
            continue
        if comment:
            comments.append(comment)
print(len(comments))
# 設置分詞
com_aft_spl = jieba.cut(
    str(comments),cut_all=False) # 非全模式分詞,cut_all=False
words = ' '.join(com_aft_spl)
print(len(words))

# 設置停用詞,在默認停用詞基礎上添加新的停用詞
stopwords = STOPWORDS.copy()
wd_libs = ['電影','一部','一個','沒有','什麼','有點','這部','這個','不是','我們',
          '真的','感覺','覺得','還是','但是','就是','流浪地球','流浪','地球','中國']
for wl in wd_libs:
    stopwords.add(wl)
print(len(stopwords))
溫馨提示:此處有坑font_path設置不好,中文詞雲可能會亂碼!
# 詞雲代碼構建
d = path.dirname('__file__')
nana_coloring = np.array(Image.open(path.join(d, "car.png"))) # 詞雲形狀由圖片‘car.png’決定
my_wordcloud = WordCloud( background_color = 'white',      # 設置背景顏色
                            mask = nana_coloring,          # 設置背景圖片
                            max_words = 200,              # 設置最大現實的字數
                            stopwords = stopwords,         # 設置停用詞
                            font_path = 'simhei.ttf',
                            max_font_size = 100,            # 設置字體最大值
                            random_state = 30             # 設置有多少種隨機生成狀態,即有多少種配色方案
                          )
my_wordcloud.generate(words)
分詞詞雲背景圖片,決定詞雲形狀。

在這裏插入圖片描述

# 可視化詞雲圖
mp.imshow(my_wordcloud,cmap=mp.cm.gray, interpolation='bilinear')    # 顯示詞雲圖
mp.axis("off")             # 不顯示x軸、y軸下標
mp.show()
my_wordcloud.to_file("wordcloud_new.png")

在這裏插入圖片描述

評語文本分析小結

  • 文本可視化看到影迷的主評價詞爲:好看,科幻,震撼,特效劇情。
  • 從影評評價中可以看出《流浪地球》的口碑非常不錯,值得一看!
項目源代碼包github地址:https://github.com/Willsgao/Personal-projects/

參考網址:https://www.jianshu.com/p/d4a86da914e9
參考網址:https://blog.csdn.net/weixin_40096730/article/details/81984231
參考網址:https://blog.csdn.net/Dick633/article/details/80261233

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章