【Python练习】五月天团员作曲统计图

一、导出歌曲名和作曲人数据

定义一个函数songname_composer,输入歌词文件txt,输出一个列表,元素是歌名及对应的作曲人。

def songname_composer(text: list) -> list:  # 从lrc文件导出歌曲名及对应作曲人
    songslst = []
    for line in text:
        if '歌曲名:' in line:
            songname_index = text.index(line)  # 歌曲名所在行数
            composer_index = songname_index + 2
            if '作曲' in text[composer_index]:
                song_name = line.split(":")[1]  # 取歌曲名
                composer = text[composer_index].split(":")[1]  # 取作曲人名字
                songslst.append([song_name, composer])
    return songslst

  读取前一篇文章第一步歌词爬取结果生成的名为“maydaylrc.txt”的歌词文件,【Python练习】生成五月天歌名词云图和歌词词频词云图_ccaere的博客-CSDN博客

 执行函数,生成含歌名及作曲人的列表name_composerlst

# 导出歌曲名和作曲人数据
lrcs = read_txt('maydaylrc.txt')  # 读取歌词TXT文件
name_composerlst = songname_composer(lrcs)  # 导出歌曲名及作曲人
# print(name_composerlst)
# print(f"共{len(name_composerlst)}首歌曲")  # 歌曲数量

二、清洗歌名数据

定义一个函数cleansongname,删除live版、日语版、20周年版之类的重复歌曲,纯音乐,以及非五月天创作歌曲,输入第一步的name_composerlst,输出纯净版的列表name_cleanlst

def cleansongname(songslst: list) -> list:  # 清洗歌曲名数据
    song_dt = {}
    nolst = (
        '缩影', '女字旁', '爱的轮回', '刚好', '她并非不想', '我还是爱着你', '无人之境', '是什么让我遇见这样的你',
        '三城记',
        '如果我是石头', '青岛巴士', '寻根(带我去三义)', '诚品激突', '武装以后(演奏曲)', '那一年的花季(探母瑄瑄版配乐)',
        '灵魂能有多重',
        '哪一楼的阿?(台北的脚步)', '三义之夏', '轻功(慢摇滚演奏版)', '寂寞星球 人人寂寞',
        '故事都随风(开往哈尔滨的列车)', '爱是绿洲',
        '鲨鱼摇滚', '火花一般', '旅途上', '企鹅午后', '公路电影', '年华', '一个人的表情', '金赛的迷惑', '…的愉快',
        'What\'s Your Story?',
        'Song for you', '成功間近', '人生有限会社', '頑固', 'Party Animal', '少年漂流記', 'Song for you', 'Buzzin’',
        'Dancin\' Dancin\'', '一歩一歩', '恋愛ING', '乾杯', '孫悟空', '末日', '明日', 'To Find My Paradise',
        'Enrich Your Life',
        '探母', '五月之恋序曲', '前传', '咖哩鱼蛋', '海豚的歌', '神的孩子都在跳舞', '刻在我心底的名字', '干啦干啦',
        '凡人歌', '玫瑰少年')
    m = u"[\u3040-\u31FF]+"  # 日文字符
    for song in songslst:
        song_name = song[0].replace(' ', '')
        # song_name = song[0].replace(",", "").replace(" ", "").replace("!", "")  # 删除歌名中的空格,逗号,感叹号
        # 删除live等不同版本
        if song[0] in nolst:
            continue
        if re.findall(m, song[0]):  # 删除日文歌曲
            continue
        if '(' in song[0]:
            song_name = song_name.split('(')[0]
        if '#' in song[0]:
            song_name = song_name.split('#')[0]
        song_dt[song_name] = song_dt.get(song_name, song[1])  # 如果歌名重复,取最后的作曲人
    songslst_result = []
    for key, value in song_dt.items():
        songslst_result.append([key, value])
    return songslst_result


name_cleanlst = cleansongname(name_composerlst)

三、清洗作曲人数据

定义一个函数cleancomposer,把作曲人名字统一,输入第二步生成的name_cleanlst,输出结果列表composer_result

def cleancomposer(name_lst: list) -> list:  # 清洗作曲人
    for composer in name_lst:
        composer[1] = composer[1].replace(' ', '')
        if '无望' in composer[1]:
            composer[1] = '阿信'
        if '五月天阿信' in composer[1]:
            composer[1] = composer[1].replace('五月天阿信', '阿信')
        if '五月天怪兽' in composer[1]:
            composer[1] = composer[1].replace('五月天怪兽', '怪兽')
        if '五月天石头' in composer[1]:
            composer[1] = composer[1].replace('五月天石头', '石头')
        if '五月天玛莎' in composer[1]:
            composer[1] = composer[1].replace('五月天玛莎', '玛莎')
        if '五月天冠佑' in composer[1]:
            composer[1] = composer[1].replace('五月天冠佑', '冠佑')
    return name_lst


# 清洗作曲人数据
composer_result = cleancomposer(name_cleanlst)
# print(composer_result)
# print(f"共{len(composer_result)}首歌曲")

四、保存作曲人数据

把第三步的列表composer_result数据写入到文件中保存

# 作曲人数据写入文件
composer_text = ''
for i in composer_result:
    composer_text += i[0] + ',' + i[1] + '\n'
write_txt("maydaycomposer.txt", composer_text)

文件数据如下图:

五、作曲数量统计

定义一个函数count_composer,单独生成一个人的作曲歌曲列表

def count_composer(name_lst: list, name: str) -> list:  # 统计作曲数量
    composelst = []
    for composer in name_lst:
        if name in composer[1]:
            composelst.append(composer[0])
    return composelst

分别对五月天五位团员的作曲数量进行统计

# 作曲数量统计
composelst_ashin = count_composer(composer_result, '阿信')
num_ashin = len(composelst_ashin)
print(f"阿信作曲共{num_ashin}首歌曲")
print(composelst_ashin)

composelst_monster = count_composer(composer_result, '怪兽')
num_monster = len(composelst_monster)
print(f"怪兽作曲共{num_monster}首歌曲")
print(composelst_monster)

composelst_stone = count_composer(composer_result, '石头')
num_stone = len(composelst_stone)
print(f"石头作曲共{num_stone}首歌曲")
print(composelst_stone)

composelst_masa = count_composer(composer_result, '玛莎')
num_masa = len(composelst_masa)
print(f"玛莎作曲共{num_masa}首歌曲")
print(composelst_masa)

composelst_ming = count_composer(composer_result, '冠佑')
num_ming = len(composelst_ming)
print(f"冠佑作曲共{num_ming}首歌曲")
print(composelst_ming)

六、绘制五月天作曲饼图

根据第五步统计的作曲数量,生成五月天作曲统计饼图

# 绘制饼图
plt.rcParams['font.family'] = 'SimHei'  # 设置显示中文
plt.rcParams['axes.unicode_minus'] = False
font = "SIMLI.TTF"

# 绘制作曲饼图
plt.figure(figsize=(16, 9))
song_x = ['阿信', '怪兽', '石头', '玛莎', '冠佑']
song_y = [num_ashin, num_monster, num_stone, num_masa, num_ming]

plt.subplot(231)
plt.title('五月天作曲统计')
plt.pie(song_y, labels=song_x, autopct='%1.2f%%')

 

七、分别生成五月天团员作曲词云图

用第五步里生成的五月天团员作曲列表,分别生成五个人作曲歌名的词云图,背景图用的每个人剪影,把生成的图片保存到文件

背景图:

阿信:

 玛莎:

 冠佑:

怪兽:

 石头:

词云图生成代码如下: 

# 生成作曲人词云
composelst_ashin_text = ' '.join(composelst_ashin)
img1 = Image.open('mask-ashin.jpg')
mask1 = np.array(img1)  # 导入词云形状
word_pic1 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask1) \
    .generate(composelst_ashin_text)  # 生成词云
word_pic1.to_file('wc-ashin.png')  # 词云保存到图片

composelst_monster_text = ' '.join(composelst_monster)
img2 = Image.open('mask-monster.jpg')
mask2 = np.array(img2)  # 导入词云形状
word_pic2 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask2) \
    .generate(composelst_monster_text)  # 生成词云
word_pic2.to_file('wc-monster.png')  # 词云保存到图片

composelst_stone_text = ' '.join(composelst_stone)
img3 = Image.open('mask-stone.jpg')
mask3 = np.array(img3)  # 导入词云形状
word_pic3 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask3) \
    .generate(composelst_stone_text)  # 生成词云
word_pic3.to_file('wc-stone.png')  # 词云保存到图片

composelst_masa_text = ' '.join(composelst_masa)
img4 = Image.open('mask-masha.jpg')
mask4 = np.array(img4)  # 导入词云形状
word_pic4 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask4) \
    .generate(composelst_masa_text)  # 生成词云
word_pic4.to_file('wc-masa.png')  # 词云保存到图片

composelst_ming_text = ' '.join(composelst_ming)
img5 = Image.open('mask-ming.jpg')
mask5 = np.array(img5)  # 导入词云形状
word_pic5 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask5) \
    .generate(composelst_ming_text)  # 生成词云
word_pic5.to_file('wc-ming.png')  # 词云保存到图片

八、图片展示

用plt对第六步、第七步生成的图片同时进行展示

# 显示词云图片
plt.subplot(232)
p1 = plt.imread('wc-ashin.png')
plt.title('阿信作曲统计')
plt.imshow(p1)
plt.axis("off")

plt.subplot(233)
p2 = plt.imread('wc-monster.png')
plt.title('怪兽作曲统计')
plt.imshow(p2)
plt.axis("off")

plt.subplot(234)
p3 = plt.imread('wc-stone.png')
plt.title('石头作曲统计')
plt.imshow(p3)
plt.axis("off")

plt.subplot(235)
p4 = plt.imread('wc-masa.png')
plt.title('玛莎作曲统计')
plt.imshow(p4)
plt.axis("off")

plt.subplot(236)
p5 = plt.imread('wc-ming.png')
plt.title('冠佑作曲统计')
plt.imshow(p5)
plt.axis("off")

plt.show()

结果图:

五月天五位团员单独图片如下:

阿信作曲歌曲:

 

 玛莎作曲歌曲:

 冠佑作曲歌曲:

 怪兽作曲歌曲:

 石头作曲歌曲:

 九、全部代码

全部代码如下:

import numpy as np
from PIL import Image
import jieba
import matplotlib.pyplot as plt
from wordcloud import WordCloud
import re


def read_txt(filename: str) -> list:  # 读取源文件
    with open(filename, "r") as f:
        text = f.read().split("\n")
    return text


def songname_composer(text: list) -> list:  # 从lrc文件导出歌曲名及对应作曲人
    songslst = []
    for line in text:
        if '歌曲名:' in line:
            songname_index = text.index(line)  # 歌曲名所在行数
            composer_index = songname_index + 2
            if '作曲' in text[composer_index]:
                song_name = line.split(":")[1]  # 取歌曲名
                composer = text[composer_index].split(":")[1]  # 取作曲人名字
                songslst.append([song_name, composer])
    return songslst


def cleansongname(songslst: list) -> list:  # 清洗歌曲名数据
    song_dt = {}
    nolst = (
        '缩影', '女字旁', '爱的轮回', '刚好', '她并非不想', '我还是爱着你', '无人之境', '是什么让我遇见这样的你',
        '三城记',
        '如果我是石头', '青岛巴士', '寻根(带我去三义)', '诚品激突', '武装以后(演奏曲)', '那一年的花季(探母瑄瑄版配乐)',
        '灵魂能有多重',
        '哪一楼的阿?(台北的脚步)', '三义之夏', '轻功(慢摇滚演奏版)', '寂寞星球 人人寂寞',
        '故事都随风(开往哈尔滨的列车)', '爱是绿洲',
        '鲨鱼摇滚', '火花一般', '旅途上', '企鹅午后', '公路电影', '年华', '一个人的表情', '金赛的迷惑', '…的愉快',
        'What\'s Your Story?',
        'Song for you', '成功間近', '人生有限会社', '頑固', 'Party Animal', '少年漂流記', 'Song for you', 'Buzzin’',
        'Dancin\' Dancin\'', '一歩一歩', '恋愛ING', '乾杯', '孫悟空', '末日', '明日', 'To Find My Paradise',
        'Enrich Your Life',
        '探母', '五月之恋序曲', '前传', '咖哩鱼蛋', '海豚的歌', '神的孩子都在跳舞', '刻在我心底的名字', '干啦干啦',
        '凡人歌', '玫瑰少年')
    m = u"[\u3040-\u31FF]+"  # 日文字符
    for song in songslst:
        song_name = song[0].replace(' ', '')
        # song_name = song[0].replace(",", "").replace(" ", "").replace("!", "")  # 删除歌名中的空格,逗号,感叹号
        # 删除live等不同版本
        if song[0] in nolst:
            continue
        if re.findall(m, song[0]):  # 删除日文歌曲
            continue
        if '(' in song[0]:
            song_name = song_name.split('(')[0]
        if '#' in song[0]:
            song_name = song_name.split('#')[0]
        song_dt[song_name] = song_dt.get(song_name, song[1])  # 如果歌名重复,取最后的作曲人
    songslst_result = []
    for key, value in song_dt.items():
        songslst_result.append([key, value])
    return songslst_result


def cleancomposer(name_lst: list) -> list:  # 清洗作曲人
    for composer in name_lst:
        composer[1] = composer[1].replace(' ', '')
        if '无望' in composer[1]:
            composer[1] = '阿信'
        if '五月天阿信' in composer[1]:
            composer[1] = composer[1].replace('五月天阿信', '阿信')
        if '五月天怪兽' in composer[1]:
            composer[1] = composer[1].replace('五月天怪兽', '怪兽')
        if '五月天石头' in composer[1]:
            composer[1] = composer[1].replace('五月天石头', '石头')
        if '五月天玛莎' in composer[1]:
            composer[1] = composer[1].replace('五月天玛莎', '玛莎')
        if '五月天冠佑' in composer[1]:
            composer[1] = composer[1].replace('五月天冠佑', '冠佑')
    return name_lst


def count_composer(name_lst: list, name: str) -> list:  # 统计作曲数量
    composelst = []
    for composer in name_lst:
        if name in composer[1]:
            composelst.append(composer[0])
    return composelst


def write_txt(filename: str, text: str) -> None:  # 将清洗后数据写入新文件
    with open(filename, "w", encoding="utf-8") as f:
        f.write(text)


# 导出歌曲名和作曲人数据
lrcs = read_txt('maydaylrc.txt')  # 读取歌词TXT文件
name_composerlst = songname_composer(lrcs)  # 导出歌曲名及作曲人
# print(name_composerlst)
# print(f"共{len(name_composerlst)}首歌曲")  # 歌曲数量

# 清洗歌曲名数据
name_cleanlst = cleansongname(name_composerlst)

# 清洗作曲人数据
composer_result = cleancomposer(name_cleanlst)
# print(composer_result)
# print(f"共{len(composer_result)}首歌曲")

# 作曲人数据写入文件
composer_text = ''
for i in composer_result:
    composer_text += i[0] + ',' + i[1] + '\n'
write_txt("maydaycomposer.txt", composer_text)

# 作曲数量统计
composelst_ashin = count_composer(composer_result, '阿信')
num_ashin = len(composelst_ashin)
print(f"阿信作曲共{num_ashin}首歌曲")
print(composelst_ashin)

composelst_monster = count_composer(composer_result, '怪兽')
num_monster = len(composelst_monster)
print(f"怪兽作曲共{num_monster}首歌曲")
print(composelst_monster)

composelst_stone = count_composer(composer_result, '石头')
num_stone = len(composelst_stone)
print(f"石头作曲共{num_stone}首歌曲")
print(composelst_stone)

composelst_masa = count_composer(composer_result, '玛莎')
num_masa = len(composelst_masa)
print(f"玛莎作曲共{num_masa}首歌曲")
print(composelst_masa)

composelst_ming = count_composer(composer_result, '冠佑')
num_ming = len(composelst_ming)
print(f"冠佑作曲共{num_ming}首歌曲")
print(composelst_ming)

# 绘制饼图
plt.rcParams['font.family'] = 'SimHei'  # 设置显示中文
plt.rcParams['axes.unicode_minus'] = False
font = "SIMLI.TTF"

# 绘制作曲饼图
plt.figure(figsize=(16, 9))
song_x = ['阿信', '怪兽', '石头', '玛莎', '冠佑']
song_y = [num_ashin, num_monster, num_stone, num_masa, num_ming]

plt.subplot(231)
plt.title('五月天作曲统计')
plt.pie(song_y, labels=song_x, autopct='%1.2f%%')

# 生成作曲人词云
composelst_ashin_text = ' '.join(composelst_ashin)
img1 = Image.open('mask-ashin.jpg')
mask1 = np.array(img1)  # 导入词云形状
word_pic1 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask1) \
    .generate(composelst_ashin_text)  # 生成词云
word_pic1.to_file('wc-ashin.png')  # 词云保存到图片

composelst_monster_text = ' '.join(composelst_monster)
img2 = Image.open('mask-monster.jpg')
mask2 = np.array(img2)  # 导入词云形状
word_pic2 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask2) \
    .generate(composelst_monster_text)  # 生成词云
word_pic2.to_file('wc-monster.png')  # 词云保存到图片

composelst_stone_text = ' '.join(composelst_stone)
img3 = Image.open('mask-stone.jpg')
mask3 = np.array(img3)  # 导入词云形状
word_pic3 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask3) \
    .generate(composelst_stone_text)  # 生成词云
word_pic3.to_file('wc-stone.png')  # 词云保存到图片

composelst_masa_text = ' '.join(composelst_masa)
img4 = Image.open('mask-masha.jpg')
mask4 = np.array(img4)  # 导入词云形状
word_pic4 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask4) \
    .generate(composelst_masa_text)  # 生成词云
word_pic4.to_file('wc-masa.png')  # 词云保存到图片

composelst_ming_text = ' '.join(composelst_ming)
img5 = Image.open('mask-ming.jpg')
mask5 = np.array(img5)  # 导入词云形状
word_pic5 = WordCloud(
    font_path=font,
    height=1800,
    width=1800,
    margin=2,
    background_color='white',
    repeat=True,
    mask=mask5) \
    .generate(composelst_ming_text)  # 生成词云
word_pic5.to_file('wc-ming.png')  # 词云保存到图片

# 显示词云图片
plt.subplot(232)
p1 = plt.imread('wc-ashin.png')
plt.title('阿信作曲统计')
plt.imshow(p1)
plt.axis("off")

plt.subplot(233)
p2 = plt.imread('wc-monster.png')
plt.title('怪兽作曲统计')
plt.imshow(p2)
plt.axis("off")

plt.subplot(234)
p3 = plt.imread('wc-stone.png')
plt.title('石头作曲统计')
plt.imshow(p3)
plt.axis("off")

plt.subplot(235)
p4 = plt.imread('wc-masa.png')
plt.title('玛莎作曲统计')
plt.imshow(p4)
plt.axis("off")

plt.subplot(236)
p5 = plt.imread('wc-ming.png')
plt.title('冠佑作曲统计')
plt.imshow(p5)
plt.axis("off")

plt.show()

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值