1. 程式人生 > >用Python分析本山大叔鬼畜視訊為啥這麼火!

用Python分析本山大叔鬼畜視訊為啥這麼火!

cxa,有著豐富的爬蟲工作經驗,公眾號Python學習開發,擅長各種爬蟲技術,熟悉大規模爬蟲開發。熱愛並喜歡鑽研python。

改革春風吹滿地,中國人民真爭氣。

用Python分析本山大叔鬼畜視訊為啥這麼火!

 

2018年年末,“改革春風吹滿地”火了。這是一個來自嗶哩嗶哩的一個鬼畜類音樂視訊。

由up主小可兒上傳,目前播放量已達到1400多萬,有著相當高的熱度。該視訊剪輯了趙本山的歷年作品的經典臺詞,配以略帶喜感的音樂(bgm由其他up主製作),每一句臺詞銜接的相當完美。在網易雲音樂裡也可以搜到同名音樂,另有別名「唸詩之王」,網易雲音樂的一位名為A96ccA的這樣聽眾評論道:

第一遍:這是啥玩意?
第二遍:嗯,還可以
第三遍:改革春風吹滿地…

可以看出同樣的是一首洗腦的音樂。

下面讓我先來欣賞(再度洗腦)一下。

下面就讓我們爬取b站上該視訊的評論內容,並進行分析為什麼這個視訊會如此的火。

資料下載

首先我們開啟視訊:https://www.bilibili.com/video/av19390801.

然後找到評論部分,開啟谷歌瀏覽器的控制檯,檢視network選項的請求資訊。通過觀察我們發現了這樣的連結:https://api.bilibili.com/x/v2/reply?callback=jQuery17204794190151297566_1546432727230&jsonp=jsonp&pn=1&type=1&oid=19390801&sort=0&_=1546432740370

去掉沒有用的資訊最後我們得到最終的url形式為:https://api.bilibili.com/x/v2/reply?pn={pn}&type=1&oid=19390801

其中pn為第幾頁,目前看到評論有1129頁,這些資料我們用作簡單的資料分析基本夠用了。

下面就可以編寫我們的程式碼了,這裡我採取的是非同步網路請求模組aiohttp。然後儲存下了每條評論的所以網頁可以得到的資訊,後期獲取每條評論的內容,為後面資料分析使用

用Python分析本山大叔鬼畜視訊為啥這麼火!

 

下面是主要爬取邏輯

base_url = "https://api.bilibili.com/x/v2/reply?pn={pn}&type=1&oid=19390801"
async def fetch(url):
 async with sem: #併發個數控制
 async with aiohttp.ClientSession() as session: #建立session
 with async_timeout.timeout(10): #等10s
 async with session.get(url) as res: 
 data = await res.json()#通過await獲取非同步過程中的資料
 print(data)
 await asyncio.sleep(2)#加個非同步等待防止被封。
 await save_data(glom.glom(data, "data.replies"))#glom模組json資料解析用。

這裡需要用到以下模組,使用pip install即可安裝

aiohttp
async_timeout
uvloop(windows就不用了,只支援unix系統)
glom

需要說明的是之前我就是因為沒有加等待時間,所以被b站這個介面的連結給封了,造成的現象就是視訊可以看但是評論是重新整理不出來的,挺有意思的。關於aiohttp的使用方法。

到這裡資料下載邏輯就完事了,下面是資料儲存邏輯。

資料儲存

因為上面的下載的結果是json格式,所以首先資料庫就是mongodb,這裡為了統一使用了非同步mongo資料模組motor,一個基於事件迴圈的模組。

首先建立資料鏈接

class MotorBase:
 _db = {}
 _collection = {}
 def __init__(self, loop=None):
 self.motor_uri = ''
 self.loop = loop or asyncio.get_event_loop()
 def client(self, db):
 self.motor_uri = f"mongodb://localhost:27017/{db}"
 return AsyncIOMotorClient(self.motor_uri, io_loop=self.loop)
 def get_db(self, db='weixin_use_data'):
 if db not in self._db:
 self._db[db] = self.client(db)[db]
 return self._db[db]

這裡使用模組有:

asyncio
motor

然後開始使用類似pymongo的方式插入資料,具體程式碼如下

async def save_data(items):
 mb = MotorBase().get_db('weixin_use_data') #獲取連結物件,weixin_use_data是我的資料庫名。
 for item in items:
 try:
 await mb.bilibili_comments.update_one({
 'rpid': item.get("rpid")},
 {'$set': item},
 upsert=True)#bilibili_comments是我的表名,update_one方法的作用是不存在就插入存在更新。
 except Exception as e:
 print("資料插入出錯", e.args,"此時的item是",item)

然後通過執行這個事件迴圈,事件迴圈是這裡所有非同步的基礎。

 loop = asyncio.get_event_loop()#建立一個事件迴圈
 loop.run_until_complete(get_data())#開始執行直到程式結束

資料解析

上面我們拿到了作出資料,但是資料都是json格式的,而且量很大,我們需要的只有評論內容,所以我們需要進一步對資料進行處理,同樣的這裡我也使用了檔案讀寫非同步模組aiofiles

這部分程式碼量也很少,用法和open file差不多,多了些非同步的形式而已。

首先讀取mongo裡的資料

async def get_data():
 mb = MotorBase().get_db('weixin_use_data')
 data=mb.bilibili_comments.find()
 return data

讀取還是用的motor模組為了配合後面的檔案讀入使用。

async def m2f():
 data = await get_data()
 async for item in data:
 t = item.get("content").get("message").strip()
 fs = await aiofiles.open(pathlib.Path.joinpath(pathlib.Path.cwd().parent, "msg.txt"), 'a+')#pathlib路徑拼接
 await fs.write(t)

到目前為止資料獲取部分基本結束了,後面就是對上面的文字檔案進行分析了。

資料分析

為了清晰的表達資料所帶來的資訊,對於評論資訊,我們選用直觀的方式--詞雲圖

安裝包

jieba
wordcloud
matplotlib

生成詞雲需要用的圖

 

用Python分析本山大叔鬼畜視訊為啥這麼火!

 

進群:960410445 即可獲取數十套PDF!

字型檔案

mac中預設字型顯示亂碼,這裡指定了別的字型msyhbd.ttf,網上隨便搜了一個,windows可以或其他系統支援字型即可

停用詞設定

經過分析大概設定瞭如下停用詞:

哈
哈哈
哈哈哈
xa0
一個
u3000
什麼
視訊
這個
up
看到
怎麼
播放
真的
知道
已經
改革
春風
滿地
鬼畜
抖音
現在
春晚
千萬
助攻

停用詞設定是為了去除一些沒有意義的詞,比如這個,那個之類的。或者當前檔案的標題

程式碼如下

# -*- coding: utf-8 -*-
# @Time : 2019/1/2 7:52 PM
# @Author : cxa
# @File : cutword.py
# @Software: PyCharm
# coding=utf-8
import jieba
import matplotlib.pyplot as plt
from wordcloud import WordCloud
# 獲取所有評論
comments = []
with open('msg.txt', mode='r', encoding='utf-8') as f:
 rows = f.readlines()
 for row in rows:
 comments.append(row)
# 設定分詞
comment_after_split = jieba.cut(str(comments), cut_all=False) #分詞,cut_all=false
words = ' '.join(comment_after_split) # 以空格進行拼接
# 設定遮蔽詞
STOPWORDS = set(map(str.strip, open('stopwords').readlines()))
print(STOPWORDS)
# 匯入背景圖
bg_image = plt.imread('1.jpeg')
# 設定詞雲引數,引數分別表示:畫布寬高、背景顏色、背景圖形狀、字型,遮蔽詞、最大詞的字型大小
wc = WordCloud(width=2024, height=1400, background_color='white', mask=bg_image,font_path='msyhbd.ttf',stopwords=STOPWORDS, max_font_size=400,
 random_state=50)
# 將分詞後資料傳入雲圖
wc.generate_from_text(words)
plt.imshow(wc)
plt.axis('off') # 不顯示座標軸
plt.show()
# 儲存結果到本地
wc.to_file('ggcfcmd.jpg')

最終結果

用Python分析本山大叔鬼畜視訊為啥這麼火!

 

由此可以看出這視訊最重要的還是洗腦,導致進來就出不去了,同樣的也是追憶本山大叔多年來帶給大家的無數快樂時光,總之洗腦就完事了。