資料視覺化豆瓣電影 TOP250

Zhiw發表於2019-02-23

我平時喜歡看電影,也會習慣性參考豆瓣電影評分,而豆瓣對於爬蟲愛好者是很友好的,沒有太多反爬措施,對新手是很友好的。

本文將爬取豆瓣電影 TOP 250榜單的資料進行視覺化,主要用了 BeautifulSoup, pandas , Matplotlib 等資料分析常用的庫。

資料爬取

首先開啟頁面,進入除錯模式,我們會看到如下頁面:

kWOG5D.md.png

如圖所示,我們可以很直觀的看到資料,圖示資訊就是我們本次要爬取的資訊。

接下來,點選頁面最下面的翻頁,我們注意到第 2 頁的地址為:movie.douban.com/top250?star… 第 3 頁的地址為:movie.douban.com/top250?star…

不難發現其規律,那就開始寫程式碼吧。

 import os
 
 import matplotlib.pyplot as plt
 import pandas as pd
 import requests
 from bs4 import BeautifulSoup
 
 def movies_spider():
    records = []
    for start in (range(250)[::25]):
        url = f"https://movie.douban.com/top250?start={start}"
        response = requests.get(url).text
        soup = BeautifulSoup(response, 'html.parser')
        movie_list = soup.find_all(class_='item')
        for item in movie_list:
            rank = int(item.find('em').string)  # 排名
            pic = item.find(class_='pic')
            href = pic.find('a')['href']  # 連結

            info = item.find(class_='info')
            name = info.find(class_='title').string  # 電影名稱
            rating_num = info.find(class_='rating_num').string  # 評分
            total = info.find(
                class_='rating_num').find_next_sibling().find_next_sibling().string[:-3]  # 評價人數
            inq = info.find(class_='inq')  # 簡評
            try:
                quote = inq.get_text()
            except AttributeError:
                quote = None
                print("Type error")
            bd_div = item.find(class_='bd')
            infos = bd_div.find('p').get_text().strip().split('\n')
            # infos = ['導演: 弗蘭克·德拉邦特 Frank Darabont\xa0\xa0\xa0主演: 蒂姆·羅賓斯 Tim Robbins /...',
            #          '                            1994\xa0/\xa0美國\xa0/\xa0犯罪 劇情']
            info1 = infos[0].split('\xa0\xa0\xa0')
            director = info1[0][4:]  # 導演
            info2 = infos[1].lstrip().split('\xa0/\xa0')
            year = info2[0][:4]
            area = info2[1]
            movie_type = info2[2]

            movie = {
                'rank': rank,
                'name': name,
                'director': director,
                'year': year,
                'area': area,
                'type': movie_type,
                'rating_num': rating_num,
                'comment_num': total,
                'quote': quote,
                'url': href
            }
            records.append(movie)
    return records
複製程式碼

程式碼配合前面的原始碼,還是很好理解的,接下來先將資料儲存為 csv 檔案,然後再利用 pandas 分析處理

headers = ['rank', 'name', 'director', 'year', 'area', 'type', 'rating_num', 'comment_num',
           'quote', 'url']
df = pd.DataFrame(rows, columns=headers)
df.to_csv('top250.csv')
複製程式碼

我們來看一下資料:

kWOXs1.md.png

資料分析和視覺化

國家地區

先分析製片的國家地區,可以看到,有的電影不止一個國家地區,比如霸王別姬的製片國家地區是:中國大陸 香港,因此我們可以用 split 進行處理

area_split = df['area'].str.split(' ').apply(pd.Series)
複製程式碼

可以看到電影最多有5個國家地區,我們進行統計,求和,最後繪圖

a = area_split.apply(pd.value_counts)
area_count = a.sum(axis=1)
area_df = pd.DataFrame(area_count, columns=['count'], dtype=int).sort_values(by='count')
area_df.plot.barh()
複製程式碼

kWOzdK.png

美國以 144 部遙遙領先,香港 25 部排名第 4,中國大陸 17 部位居第 7

  • 美國:144

  • 日本:34

  • 英國:34

  • 香港:25

  • 法國:21

電影型別

我們以同樣的方法分析分析電影型別

kWXSIO.png

劇情片 191 部同樣遙遙領先,愛情、冒險、喜劇和犯罪,也是大家喜歡的型別。

  • 劇情:192

  • 愛情:57

  • 冒險:47

  • 喜劇:47

  • 犯罪:44

導演

前5的導演是:

  • 克里斯托弗·諾蘭:7

  • 宮崎駿:6

  • 王家衛:5

  • 史蒂文·斯皮爾伯格:5

  • 李安:5

這幾位導演真是實至名歸

評分

首先看一下排名前 10 的電影

排名 電影 評分
1 肖申克的救贖 9.6
33 控方證人 9.6
2 霸王別姬 9.6
5 美麗人生 9.5
8 辛德勒的名單 9.5
3 這個殺手不太冷 9.4
4 阿甘正傳 9.4
32 十二怒漢 9.4
14 放牛班的春天 9.3
217 城市之光 9.3

注意到《城市之光》以 9.3 分排名 217,那麼我們就會有疑問,評分與排名之間有什麼關係呢,我們通過繪製散點圖和直方圖來分析

df.plot.scatter(x='rating_num', y='rank')
plt.title('評分與排名關係')
plt.xlabel('評分')
plt.ylabel('排名')
plt.gca().invert_yaxis()

df['rating_num'].plot.hist(bins=10, rwidth=0.9)
plt.title('評分分佈')
複製程式碼

kWXJe0.png
kWXQzj.png

從上圖分析,隨著評分升高,排名也基本靠前,評分主要集中在 8.4~9.2 之間。同時可以通過 pandas 計算平均數,眾數和相關係數,平均分為 8.83 分,眾數為 8.7 分,而相關係數為 -0.6882,評分與排名強相關。

評價人數

評價人數前 10 電影

kWXaYF.png

用之前同樣的方法,我們來分析評價人數的分佈情況以及評價人數和排名之間的關係

kWXdW4.png
kWX0SJ.png

與評分不同的是,隨著評價人數的增多,電影排名有提前的趨勢,評價人數主要分佈在 10w-50w 之間,平均值為 34.36w,相關係數為 -0.6865,評價人數與排名強相關。

年份

kWXBl9.png
kWXrO1.png

電影主要集中在 1990 年以後,相關係數為 0.0173,年份與排名沒有相關性。

最早的電影是在 1931 年,卓別林的《城市之光》

最近的電影是在 2017 年,三部

  • 《請以你的名字呼喚我》:117

  • 《三塊廣告牌》:191

  • 《尋夢環遊記》:63

電影數量前三的年份分別是:

  • 2010:14

  • 2004:12

  • 1994:11

沒想到貢獻了三部前 5 的電影大年 1994 也只能屈居第 3 位,最後我們來看看貢獻數量最多的 2010 年都有哪些佳作

排名 電影
9 盜夢空間
24 怦然心動
68 讓子彈飛
86 禁閉島
99 告白
118 馴龍高手
123 神偷奶爸
125 借東西的小人阿莉埃蒂
128 歲月神偷
142 黑天鵝
155 玩具總動員3
163 你看起來好像很好吃
214 初戀這件小事
237 國王的演講

結語

本文僅對資料進行簡單的爬取分析和視覺化,目的在於學習這些庫的基本使用,你還可以進行深度挖掘分析,比如可以進一步分析評價人數,評分,排名的關係,分析演員,語言以及時長等等,一個好的思路可能比技術更重要。

最後上一個 TOP250 全家福

kWXhSH.md.jpg

願你在電影中遇見另一個世界

願你在編碼中感受學習的快樂

如果你對 Python 開發以及全棧工程師感興趣,歡迎關注微信公眾號,這裡不止 Python 哦

資料視覺化豆瓣電影 TOP250

相關文章