Bilibili综合分析

前言

最近在裸睡的猪上看到一篇关于B站的文章,觉得分析的很透彻,所以小试牛刀,自己也写了一些可视化程序和分析。
数据提供了B站视频排行榜中的各类信息,比如:‘作者’,‘硬币数’,'弹幕数’等共14项信息,很全面。
项目使用python3在Jupyter notebook上开发。开发过程中使用pandas、numpy对数据进行清洗,可视化使用的是pyecharts。
这里是pyecharts中文手册地址,可支持的图形有很多同时提供了不少案例和视图,而且相较于 Matplotlib更加美观。

一、分析角度

首先从总体情况进行分析,之后分析综合排名top100的视频类别。

1. 总体情况

总体情况部分包括:
1. 各分区播放量情况。
2. 各区三连(硬币、收藏、点赞)情况。
3. 弹幕、评论、转发情况。
4. 绘制综合词云图,查看关键词汇。

2. 综合排名top100

综合排名top100部分包括:
1. top100类别占比。
2. top100播放量情况。
3. 硬币、收藏、点赞平均人数分布。
4. 各分区平均评论、弹幕、转发量情况。

二、可视化分析

1. 前期准备

1.1) 导库

首先导入pandas、numpy、pyecharts相关包并读取文件

import pandas as pd
import numpy as np
from pyecharts.charts import Pie, Bar, Map, WordCloud,Line,Grid,Scatter,Radar,Page
from pyecharts import options as opts
from pyecharts.globals import SymbolType
from pyecharts.globals import ThemeType
from pyecharts.commons.utils import JsCode
df = pd.read_csv('bilibili.csv')
df.head()

修改列名称为中文,此处修改中文列名仅为便开发,工作中不推荐中文列名。

df.columns=['作者','硬币数','弹幕数','喜欢人数','视频编号',
            '点赞数','排名','区类别','评论数','分数',
            '转发数', '标签名称','视频名称','播放次数']

Bilibili综合分析_第1张图片

1.2) 数据处理

查看数据信息、空值、重复值以及数据类型,但由于数据很完整这里不再做过多操作。

df.info()
df.isnull().count()
df.nunique().count()
df.dtypes

对数据进行拆分、聚合,方便之后各项分析,由于“区类别”列中的“全站”是各分类中排名靠前的视频,会出现重复数据,因此对其进行去除。

#剔除全区排名
df_nall=df.loc[df['区类别']!='全站']
df_nall['区类别'].value_counts()
#按分数进行排序asc
df_top100 = df_nall.sort_values(by='分数',ascending=False)[:100]
df_type = df_nall.drop(['作者','视频编号','标签名称','视频名称','排名'],axis=1)
gp_type = df_type.groupby('区类别').sum().astype('int')
type_all = gp_type.index.tolist()

总体数据概览

gp_type

Bilibili综合分析_第2张图片

2.总体情况可视化

2.1) 各分区播放情况

开始使用了柱状图,但显示效果不佳,因此替换成饼图,相较于柱状图与折线图,饼图更能够体现出个体在总体中的占比。

play = [round(i/100000000,2) for i in gp_type['播放次数'].tolist()]

# bar = (Bar()
#             .add_xaxis(type_all)
#             .add_yaxis("", play)
#             .set_global_opts(
#             title_opts=opts.TitleOpts(title="各分区播放量情况"),
#             yaxis_opts=opts.AxisOpts(name="次/亿"),
#             xaxis_opts=opts.AxisOpts(name="分区",axislabel_opts={"rotate":45})
#         )
#     )
# bar.render_notebook()

pie = (
    Pie()
    .add(
        "",
        [list(z) for z in zip(type_all, 
                              play)],
        radius=["40%", "75%"],
    )
    .set_global_opts(
        title_opts=opts.TitleOpts(title="各分区播放量情况  单位:亿次"),
        legend_opts=opts.LegendOpts(
            orient="vertical", pos_top="15%", pos_left="2%"
        ),
    )
    .set_series_opts(label_opts=opts.LabelOpts(formatter="{b}: {c}"))
)
pie.render_notebook()

Bilibili综合分析_第3张图片
播放量排名前三的分别是生活类、动画类、鬼畜类。其中动画类和鬼畜类,这两个是B站的特色。
第三、四位是音乐类和科技类。

2.2) 各区三连量情况

coin_all = [round(i/1000000,2) for i in gp_type['硬币数'].tolist()]
like_all = [round(i/1000000,2) for i in gp_type['点赞数'].tolist()]
favourite_all = [round(i/1000000,2) for i in gp_type['喜欢人数'].tolist()]
def bar_base() -> Bar:
    c = (
        Bar()
        .add_xaxis(type_all)
        .add_yaxis("硬币", coin_all)
        .add_yaxis("点赞", like_all)
        .add_yaxis("收藏", favourite_all)
        .set_global_opts(title_opts=opts.TitleOpts(title="各分区三连情况"),
                        yaxis_opts=opts.AxisOpts(name="次/百万"),
                        xaxis_opts=opts.AxisOpts(name="分区",
                                                 axislabel_opts={"rotate":45}))
    )
    return c
        
bar_base().render_notebook()

Bilibili综合分析_第4张图片
虽然生活类投币和点赞数依然是不可撼动的,但是收藏数却排在动画之后,科技类收藏升至第四位。

2.3) 弹幕、评论、分享情况

danmaku_all = [round(i/100000,2) for i in gp_type['弹幕数'].tolist()]
reply_all = [round(i/100000,2) for i in gp_type['评论数'].tolist()]
share_all = [round(i/100000,2) for i in gp_type['转发数'].tolist()]

line = (
        Line()
        .add_xaxis(type_all)
        .add_yaxis("弹幕", danmaku_all,label_opts=opts.LabelOpts(is_show=False))
        .add_yaxis("评论", reply_all,label_opts=opts.LabelOpts(is_show=False))
        .add_yaxis("转发", share_all,label_opts=opts.LabelOpts(is_show=False))
        .set_global_opts(
            title_opts=opts.TitleOpts(title="弹幕、评论、转发情况"),
            tooltip_opts=opts.TooltipOpts(trigger="axis", axis_pointer_type="cross"),
            yaxis_opts=opts.AxisOpts(name="人数 单位:十万"),
            xaxis_opts=opts.AxisOpts(name="时间(日)",axislabel_opts={"rotate":45})
            )
        )
line.render_notebook()

Bilibili综合分析_第5张图片

2.4) 热门标签词云图

tag_list=','.join(df_nall['标签名称']).split(',')
tags_count=pd.Series(tag_list).value_counts()

wordcloud = (
    WordCloud()
    .add("",
         [list(z) for z in zip(tags_count.index,tags_count)], 
         word_size_range=[10, 100])
    .set_global_opts(title_opts=opts.TitleOpts(title="热门标签"))
)
wordcloud.render_notebook()

Bilibili综合分析_第6张图片
搞笑依然是B站热门视频中出现频率最多的标签,鬼畜也依旧在显眼位置,也有不少紧跟时事的词汇。

3.综合排名可视化

3.1) top100类别占比

def pie_rosetype(col) -> Pie:
#     v = Faker.choose()
    c = (
        Pie()
        .add(
            "",
            [list(z) for z in zip(col.index.tolist(), 
                                  col.values.tolist())],
            radius=["30%", "75%"],
            center=["50%", "50%"],
            rosetype="radius",
            label_opts=opts.LabelOpts(is_show=False),
        )

        .set_global_opts(title_opts=opts.TitleOpts(title="top100类别占比"))
        .set_series_opts(label_opts=opts.LabelOpts(formatter="{b}: {c}"))
    )
    return c
pie_rosetype(df_top100['区类别'].value_counts()).render_notebook()

Bilibili综合分析_第7张图片
对比总体各分区播放情况,top100各类占比基本保持不变。

3.2) top100播放量情况

gp_play = df_top100.groupby('区类别')['播放次数'].sum()
gp_play.index.tolist()
gp_play.values.tolist()

c = (
    Bar()
    .add_xaxis(gp_play.index.tolist())
    .add_yaxis("播放量", gp_play.values.tolist(), category_gap="60%")
    .set_series_opts(itemstyle_opts={
        "normal": {
            "color": JsCode("""new echarts.graphic.LinearGradient(0, 0, 0, 1, [{
                offset: 0,
                color: 'rgba(0, 244, 255, 1)'
            }, {
                offset: 1,
                color: 'rgba(0, 77, 167, 1)'
            }], false)"""),
            "barBorderRadius": [30, 30, 30, 30],
            "shadowColor": 'rgb(0, 160, 221)',
        }})
    .set_global_opts(title_opts=opts.TitleOpts(title="top100播放量情况"))
)
c.render_notebook()

Bilibili综合分析_第8张图片
值得注意的是这段代码中有JS渲染的部分,需要导入
from pyecharts.commons.utils import JsCode,图形颜色可以在color处调,我这里就直接引用官方默认颜色了。
top100播放量与各类占比相呼应。

3.3) 硬币、收藏、点赞平均人数分布

gp_triple_quality = df_top100.groupby('区类别')[['硬币数','喜欢人数','点赞数',]].mean().astype('int')
gp_index = gp_triple_quality.index.tolist()
gp_coin = gp_triple_quality['硬币数'].values.tolist()
gp_favorite = gp_triple_quality['喜欢人数'].values.tolist()
gp_like = gp_triple_quality['点赞数'].values.tolist()
max_num = max(gp_triple_quality.values.reshape(-1))

def radar_base() -> Radar:
    c = (
        Radar()
        .add_schema(
            schema=[
                opts.RadarIndicatorItem(name=gp_index[0], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[1], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[2], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[3], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[4], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[5], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[6], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[7], max_=600000),
                opts.RadarIndicatorItem(name=gp_index[8], max_=600000),]
 
        )
        .add("硬币数", [gp_coin],color='#40e0d0')
        .add("喜欢人数", [gp_favorite],color='#1e90ff')
        .add("点赞数", [gp_like],color='#b8860b')
        .set_series_opts(label_opts=opts.LabelOpts(is_show=False),
                        linestyle_opts=opts.LineStyleOpts(width=3,type_='dotted'),)
        .set_global_opts(title_opts=opts.TitleOpts(title="硬币、收藏、点赞平均人数分布"))
    )
    return c
radar_base().render_notebook()

Bilibili综合分析_第9张图片
生活区的平均投币和点赞量依然高于动画区。投币、点赞、收藏最高的分区分别是:生活、影视、时尚。除了时尚区外,其他分区的收藏量均低于投币和点赞,且时尚区的收藏量是远高其点赞和投币量。

3.4) 各分区平均评论、弹幕、转发量情况

gp_keydata = df_top100.groupby('区类别')[['评论数','弹幕数','转发数',]].mean().astype('int')
gp_index = gp_keydata.index.tolist()
reply = [i/10000 for i in gp_keydata['评论数'].tolist()]
danmaku = [i/10000 for i in gp_keydata['弹幕数'].tolist()]
share = [i/10000 for i in gp_keydata['转发数'].tolist()]


grid = Grid()
bar = Bar()
grid.theme = ThemeType.PURPLE_PASSION
line = Line()


bar.add_xaxis(gp_index)
bar.add_yaxis("评论数",reply,label_opts=opts.LabelOpts(is_show=True))
# bar.add_yaxis("弹幕数",danmaku,label_opts=opts.LabelOpts(is_show=False))

bar.extend_axis(yaxis=opts.AxisOpts(type_="value",
                                     name="转发与弹幕量 单位:万",
                                     min_=0,
                                     max_=15,
                                     position="right",                    
                                     axislabel_opts=opts.LabelOpts(formatter="{value}万人次"),
                                     ))

bar.set_global_opts(yaxis_opts=opts.AxisOpts(
                                            name="评论量 单位:万",
                                            type_="value",
                                            min_=0,
                                            max_=15,
                                            axislabel_opts=opts.LabelOpts(formatter="{value}万人次")
                                            ), 
                    title_opts=opts.TitleOpts("各分区评论、弹幕、转发量情况"),
                    tooltip_opts=opts.TooltipOpts(trigger="axis", axis_pointer_type="cross"),
                   ) # 交叉指向工具

line.add_xaxis(gp_index)
line.add_yaxis("转发数",share,yaxis_index = 1,label_opts=opts.LabelOpts(is_show=False))
line.add_yaxis("弹幕数",danmaku,yaxis_index = 1,label_opts=opts.LabelOpts(is_show=False))

# 把line添加到bar上
bar.overlap(line)
# 这里如果不需要grid也可以,直接设置bar的格式,然后显示bar即可
# bar.render_notebook()
grid.add(chart = bar,grid_opts = opts.GridOpts(),is_control_axis_index = True)
grid.render_notebook()

Bilibili综合分析_第10张图片

三、分析结果

  1. 从数据可视化中可以看到,播放量排名前三的分别是生活类、动画类、鬼畜类,让人诧异的是以动漫起家的B站,播放量最多的视频分类竟然是生活类节目。
    第三四位分别是音乐类和科技类,突然想起那句流行语“我在B站看番,你却在B站学习”。
    近几年各类网络培训课程的出现,也让B站也逐渐成为了“充电小破站”。对于B站而言,年轻用户居多,学习氛围也就具备了较好的基础。虽然生活类投币和点赞数依然是不可撼动的,但是收藏数却排在动画之后,科技类收藏升至第四位。
  2. 搞笑依然是B站热门视频中出现频率最多的标签,鬼畜也依旧在显眼位置。从词云中能找到不少与生活密切关联的标签,有我们正在经历的抗击肺炎大作战,也有每次都订立目标,但总是败给吃吃吃的瘦身塑形和减肥。
  3. 对比总体各分类播放情况,top100各类占比基本保持不变。生活类的平均投币和点赞量依然高于动画类。投币、点赞、收藏最高的分区分别是:生活、影视、时尚。除了时尚区外,其他分区的收藏量均低于投币和点赞,且时尚区的收藏量是远高其点赞和投币量。

B站从番剧,cosplay,漫画,动画,舞蹈,音乐,鬼畜再到各种纪录片,学习资料,搞笑,电视剧,时尚,直播等等,覆盖了现在年轻人娱乐的各个领域,你可以在B站上找到任何你想要的东西,而且如今B站不光光是年轻人的娱乐场所,还是一个重要的年轻人学习的网站,接近2000万人在B站学习,成为国内最大的自学平台之一 。
如今二次元的业务已经不是B站的主营业务了,毕竟B站是需要赚钱存活的,需要进行转型,游戏、直播、广告这些已经成为了B站的主营业务,流量爆炸的时代,最令人头痛的便是如何变现,拥有庞大流量的B站显然是发现了其中的门路。

你可能感兴趣的:(练习)