真人传:1.处理男女歌词任务

文章讲述了如何使用Python编程语言,结合正则表达式,从包含男女声标注的歌词文本中分别提取出男声和女声的部分,提供了一个实际的代码示例来实现这一功能。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

前言:我有一首喜欢的“老‘歌《当爱已成往事》(李宗盛、林忆莲),这首歌的歌词由男、女声组成。假设我们已经得到了这首歌词的男女标注版(见附),你要和女(男)朋友一起唱歌,想将男(女)声单独提取出来到一个txt文件中该怎么办呢?这是我处理的一些思路。


歌词文本

女:往事不要再提 人生已多风雨

纵然记忆抹不去 爱与恨都还在心里

真的要断了过去 让明天好好继续

你就不要再苦苦追问我的消息

男:爱情它是个难题 让人目眩神迷

忘了痛或许可以 忘了你却太不容易

你不曾真的离去 你始终在我心里

我对你仍有爱意 我对自己无能为力

因为我仍有梦 依然将你放在我心中

总是容易被往事打动 总是为了你心痛

女:别流连岁月中 我无意的柔情万种
不要问我是否再相逢 不要管我是否言不由衷

女:为何你不懂(男:别说我不懂)

女:只要有爱就有痛(男:有爱就有痛)

女:有一天你会知道

女:人生没有我并不会不同(男:没有你会不同)

女:人生已经太匆匆

女:我好害怕总是泪眼朦胧(男:你泪眼朦胧)

女:忘了我就没有痛(男:忘了你也没有用)

女:将往事留在风中

女:往事不要再提 人生已多风雨

纵然记忆抹不去 爱与恨都还在心里

真的要断了过去 让明天好好继续

你就不要再苦苦追问我的消息

女:为何你不懂(男:别说我不懂)

女:只要有爱就有痛(男:有爱就有痛)

女:有一天你会知道

女:人生没有我并不会不同(男:没有你会不同)

女:人生已经太匆匆

女:我好害怕总是泪眼朦胧(男:你泪眼朦胧)

女:忘了我就没有痛(男:忘了你也没有用)

女:将往事留在风中(男:将往事留在风中)

女:为何你不懂(男:别说我不懂)

女:只要有爱就有痛(男:有爱就有痛)

女:有一天你会知道

女:人生没有我并不会不同(男:没有你会不同)

女:人生已经太匆匆

女:我好害怕总是泪眼朦胧(男:你泪眼朦胧)

女:忘了我就没有痛(男白:忘了你也没有用)

女:将往事留在风中

思路讲解

观察

我们看到,这个歌词文本有一些特点

  1. 开头往往有标注“男”或者“女"来表示这一段由谁唱
  2. 但有特殊情况:如果该段前面没有标注,说明仍在“延续”之前的角色
  3. 括号内的歌词表示该段其实是合唱

分析

题主的思路是:

1. 解决区分男女歌词的问题

  • 读取文件,将内容读到列表中,变为可迭代的对象
  • 遍历每一行歌词,但在循环之外设置参照变量sign(sign用来判断是否提取该段歌词)
  • 如果歌词开头是女,则将sign设置为True,然后提取这一段内容。如果歌词开头是男,则将x设置为False,不提取该段内容

2. 其次解决开头没有角色标注的情况(其实1已经解决了这个问题)

  • 如果开头没有角色,则延续sign的状态,比如说:

女:往事不要再提 人生已多风雨
纵然记忆抹不去 爱与恨都还在心里
真的要断了过去 让明天好好继续b
你就不要再苦苦追问我的消息

这个里面"纵然记忆抹不去 爱与恨都还在心里"这一行因为没有角色,所以sign仍是上一段的女(True),因而如果要提取女声,这一段的内容也会被提取

3. 解决括号内问题

  • 运用正则表达式,将括号内的内容替换为空白
  • 如果提取女声,则当该段的参考变量sign是女且其后有括号内容(男声)时,将男生剔除
  • 反之,如果括号内有女声的话(虽然这首歌里括号内都是男声),此时应该是参考变量sign是男且其后有括号内容(女声),则提取括号内内容

代码展示

import re
f = open(r"C:\Users\HW\Desktop\record.txt","r+",encoding="utf-8")
# 读取txt文件中的歌词
l = list(f)
# 定义一个函数,接受一个参数x,只能是"男"或"女"
def switch_gender(x):
    # 判断x是否是"男"或"女"
    if x == "男" or x == "女":
        # 如果x是"男",就将x设置为"女"
        if x == "男":
            x = "女"
        # 如果x是"女",就将x设置为"男"
        else:
            x = "男"
        # 返回x的值
        return x
   
# 定义一个函数,根据前缀提取歌词
def extract_lyrics(prefix, lyrics):
    result = ""
    # 定义一个变量,记录当前的主语是男还是女
    subject = prefix
    unsubject = switch_gender(subject)
    sign = subject
    for line in lyrics:
        # 如果行以前缀开头,就提取歌词,并更新主语
        if line[0]== subject:
            sign = subject
        else:
            if unsubject in line:
                sign = unsubject

        if sign == subject:
            pattern = r"\(.*?\)"
            replace = ""
            line_x = re.sub(pattern, replace, line)
            result += line_x + "\n"
        else:
            if subject in line:
                index = line.find(subject)
                plc =  line.find(":",index,len(line))
                result += line[plc+1:-2] + "\n"+ "\n"

    return(result)    
             
# 提取男声要唱的歌词
male_lyrics = extract_lyrics("男",l)
# 提取女生要唱的歌词
female_lyrics = extract_lyrics("女",l)

# 打印到文档中
geci =  open(r"C:\Users\HW\Desktop\歌词.txt","w+",encoding="utf-8")
geci.write(female_lyrics)
geci.close()

关于文件的位置请大家自己注意哦,记得import re 题主测试了一下,结果如下:
(注:括号内内容提取后经过处理没有保存角色标注(你将在男声末尾看到这一点))

女:往事不要再提 人生已多风雨



纵然记忆抹不去 爱与恨都还在心里



真的要断了过去 让明天好好继续



你就不要再苦苦追问我的消息



女:别流连岁月中 我无意的柔情万种

不要问我是否再相逢 不要管我是否言不由衷



女:为何你不懂



女:只要有爱就有痛



女:有一天你会知道



女:人生没有我并不会不同



女:人生已经太匆匆



女:我好害怕总是泪眼朦胧



女:忘了我就没有痛



女:将往事留在风中



女:往事不要再提 人生已多风雨



纵然记忆抹不去 爱与恨都还在心里



真的要断了过去 让明天好好继续



你就不要再苦苦追问我的消息



女:为何你不懂



女:只要有爱就有痛



女:有一天你会知道



女:人生没有我并不会不同



女:人生已经太匆匆



女:我好害怕总是泪眼朦胧



女:忘了我就没有痛



女:将往事留在风中



女:为何你不懂



女:只要有爱就有痛



女:有一天你会知道



女:人生没有我并不会不同



女:人生已经太匆匆



女:我好害怕总是泪眼朦胧



女:忘了我就没有痛



女:将往事留在风中

男:爱情它是个难题 让人目眩神迷



忘了痛或许可以 忘了你却太不容易



你不曾真的离去 你始终在我心里



我对你仍有爱意 我对自己无能为力



因为我仍有梦 依然将你放在我心中



总是容易被往事打动 总是为了你心痛



别说我不懂

有爱就有痛

没有你会不同

你泪眼朦胧

忘了你也没有用

别说我不懂

有爱就有痛

没有你会不同

你泪眼朦胧

忘了你也没有用

将往事留在风中

别说我不懂

有爱就有痛

没有你会不同

你泪眼朦胧

忘了你也没有用

感谢看到最后,如果有帮到你,不胜荣幸!关于代码的问题可以私信题主~(仅限文章代码相关问题)
结了让我们再分享一首《山丘》

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Masaki SA

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值