一、完整题目:语音识别结果的正则表达式提取

题目背景(基于样卷A/C/D模块三任务)

在AI应用系统开发中,语音识别模块的输出常为XML格式字符串。例如,识别结果为:

人工智能工程化应用

您需要编写Python代码,使用正则表达式(re模块)提取标签中的文本内容(即"人工智能工程化应用")。此任务模拟实际竞赛中语音接口的集成场景。

题目描述

补全以下Python函数,实现从XML字符串中提取目标文本的功能:

A[需要处理多重标签?] -->|是| B[采用.*?非贪婪模式]

A -->|否| C{内容含特殊字符?}

C -->|是| D[使用[^<]*精确匹配]

C -->|否| E[.*贪婪模式+长度验证]

import re

def extract_rawtext(xml_string):
    """
    从XML格式字符串中提取<rawtext>标签内的文本。
    
    参数:
        xml_string (str): XML格式的输入字符串
    
    返回:
        str: 提取出的文本内容;若无匹配则返回None
    """
    # 补全正则表达式模式(在下方<1>处填写)
    pattern = r'<rawtext>(.*?)</rawtext>'
    
    # 使用re.search匹配模式
    match = re.search(pattern, xml_string)
    
    if match:
        return match.group(1)  # 返回分组捕获的内容
    else:
        return "没有找到任何内容,请检查正则表达式"

# 测试用例
test_xml = "<result><rawtext>人工智能工程化应用</rawtext></result>"
print(extract_rawtext(test_xml))  # 预期输出: "人工智能工程化应用"
没有找到任何内容,请检查正则表达式

二、正式学习Python re 模块

Python 的 re 模块是用于处理正则表达式的标准库模块。

正则表达式(Regular Expression,简称 regex 或 regexp)是一种强大的工具,用于匹配、搜索和操作文本。

通过 re 模块,你可以在 Python 中使用正则表达式来处理字符串。

为什么使用 re 模块?

在处理文本时,我们经常需要查找特定的模式或替换某些字符。例如,验证电子邮件地址、提取网页中的链接、或者格式化文本。手动编写代码来完成这些任务可能会非常繁琐,而正则表达式提供了一种简洁且高效的方式来解决这些问题。

re 模块的基本用法

1.导入模块

#import re

常用模块

re.match() 函数用于从字符串的起始位置匹配正则表达式。如果匹配成功,返回一个匹配对象;否则返回 None。

pattern=r"hello"
data='hello world'
match=re.match(pattern,data)
if match:
    print("匹配成功:",match.group())
else:
    print("匹配成功")
匹配成功: hello

re.search() 函数用于在字符串中搜索正则表达式的第一个匹配项。与 re.match() 不同,re.search() 不要求匹配从字符串的起始位置开始。

pattern=r"world"
match=re.search(pattern,data)
if match:
    print("匹配成功",match.group())
else:
    print("匹配失败")
匹配成功 world

re.findall() 函数用于查找字符串中所有与正则表达式匹配的子串,并返回一个列表。

\d 表示“digit”,也就是单个数字字符,等价于 [0-9]。

  • 是正则里的量词,表示“匹配前一个元素一次或多次”。
pattern=r'\d+'
text="There are 3 apples and 5 oranges"
match=re.findall(pattern,text)
print("找到数字",match)
找到 ['3', '5']

re.sub(‘替换目标’,‘替换内容’,‘被查找的文本内容’) 函数用于替换字符串中与正则表达式匹配的部分

pattern =r'apple'
text='I have an apple'
new_text=re.sub(pattern,"banana",text)
print("替换后的文本:",new_text)
替换后的文本: I have an banana

正则表达式的基本用法

1 普通字符(如字母、数字)直接匹配他们自身

pattern=r'cat'
text='The cat is on the mat'
match=re.search(pattern,text)
if match:
    print("匹配成功",match.group())
匹配成功 cat

特殊字符

正则表达式中有一些特殊字符、他们具有特殊含义,例如:
.:匹配任意单个字符(除了换行符)。
*:匹配前面的字符零次或多次。
+:匹配前面的字符一次或多次。
?:匹配前面的字符零次或一次。
\d:匹配任意数字字符(等价于 [0-9])。
\w:匹配任意字母、数字或下划线字符(等价于 [a-zA-Z0-9_])。

pattern=r"\d+" # d:表示数字 +表示连续的 总体来说匹配连续的数字 如果没有+ 则匹配到1
text='The price is 100 dollars'
match=re.search(pattern,text)
if match:
    print("匹配成功",match.group())
    
pattern=r"\d" # d:表示数字 +表示连续的 总体来说匹配连续的数字 如果没有+ 则匹配到1
text='The price is 100 dollars'
match=re.search(pattern,text)
if match:
    print("匹配成功",match.group())
匹配成功 100
匹配成功 1

特殊字符 字符及用于匹配一组字符中的任意一个。列如[abc] 匹配a、b或c。

方括号 […]。

[aeiou] 的意思是:匹配集合里任意 一个字符。
就像一个“字符篮子”,里面放了 a、e、i、o、u。
正则引擎在文本里扫到任意一个,就算匹配成功。

因为你用的是 re.findall,它会找到所有非重叠的匹配结果。

所以在 “Hello world” 里:

扫到 e → 匹配

扫到 o → 匹配

扫到第二个 o → 匹配

最终结果:[‘e’, ‘o’, ‘o’]

pattern=r"[aeiou]"
text="Hello world"
matches=re.findall(pattern,text)
print("找到元音字母",matches)
找到元音字母 ['e', 'o', 'o']

分组 分组允许我将多个字符组合在一起,并对他们进行操作,列如,(abc)匹配abc。

pattern=r'(ab)+'
text='ababab'
match =re.search(pattern,text)
if match:
    print("匹配成功",match.group())
匹配成功 ababab

分组 如果把连续的+放到括号内则只会匹配到ab,个人觉得可以理解为作用域

pattern=r'(ab+)'
text='ababab'
match =re.search(pattern,text)
if match:
    print("匹配成功",match.group())
匹配成功 ab

实践练习

练习验证邮箱地址

^
锚点,表示匹配字符串的开头。

[a-zA-Z0-9_.±]+

[a-zA-Z0-9_.±]:字符类,表示字母(大小写)、数字、下划线 _、点 .、加号 +、减号 -。

+:一个或多个。
👉 这一段对应邮箱的 用户名部分(@ 前面那一截,比如 example 或 abc.123)。

@
字面量的 at 符号,邮箱必须有。

[a-zA-Z0-9-]+

允许字母、数字和连字符 -。
👉 这是 域名的第一部分,比如 example 或 mail-server。

.
匹配字面上的点号 .(因为 . 在正则里本来表示“任意字符”,所以要用 . 转义)。

[a-zA-Z0-9-.]+

字母、数字、点 .、减号 -。
👉 这是 域名的后缀(比如 com、co.uk、org.cn)。

$
锚点,表示匹配字符串的结尾。

pattern = r'^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+$'
email='example@example.com'
match=re.match(pattern,email)
if match:
    print("有效的电子邮件地址")
else:
    print("无效的电子邮件地址")
有效的电子邮件地址

用户输入验证

pattern = r'^[a-zA-Z0-9_.+-]+@[a-zA-Z0-9-]+\.[a-zA-Z0-9-.]+$'
email=input("请输入需要验证的邮箱地址:")
match=re.match(pattern,email)
if match:
    print("有效的电子邮件地址")
else:
    print("无效的电子邮件地址")
有效的电子邮件地址

练习二:提取电话号码

pattern = r"\d{3}-\d{3}-\d{4}"
text = "My phone number is 123-456-7890."
match=re.search(pattern,text)
if match:
    print("找到电话号码",match.group())
else:
    print("没有找到电话号码")
找到电话号码 123-456-7890

正则表达式元字符部分

元字符说明示例匹配
**<font style="color:rgb(51, 51, 51);">.</font>**匹配任意字符(除换行符)<font style="color:rgb(51, 51, 51);">a.c</font><font style="color:rgb(51, 51, 51);">'abc'</font>
**<font style="color:rgb(51, 51, 51);">\d</font>**匹配数字<font style="color:rgb(51, 51, 51);">\d+</font><font style="color:rgb(51, 51, 51);">'123'</font>
**<font style="color:rgb(51, 51, 51);">\D</font>**匹配非数字<font style="color:rgb(51, 51, 51);">\D+</font><font style="color:rgb(51, 51, 51);">'abc'</font>
**<font style="color:rgb(51, 51, 51);">\w</font>**匹配单词字符(字母、数字、下划线)<font style="color:rgb(51, 51, 51);">\w+</font><font style="color:rgb(51, 51, 51);">'Ab_1'</font>
**<font style="color:rgb(51, 51, 51);">\W</font>**匹配非单词字符<font style="color:rgb(51, 51, 51);">\W+</font><font style="color:rgb(51, 51, 51);">'!@#'</font>
**<font style="color:rgb(51, 51, 51);">\s</font>**匹配空白字符(空格、制表符等)<font style="color:rgb(51, 51, 51);">\s+</font><font style="color:rgb(51, 51, 51);">' \t'</font>
**<font style="color:rgb(51, 51, 51);">\S</font>**匹配非空白字符<font style="color:rgb(51, 51, 51);">\S+</font><font style="color:rgb(51, 51, 51);">'abc'</font>
**<font style="color:rgb(51, 51, 51);">[]</font>**字符集合<font style="color:rgb(51, 51, 51);">[A-Za-z]</font> → 任意字母
**<font style="color:rgb(51, 51, 51);">^</font>**匹配字符串开头<font style="color:rgb(51, 51, 51);">^\d+</font> → 开头的数字
**<font style="color:rgb(51, 51, 51);">$</font>**匹配字符串结尾<font style="color:rgb(51, 51, 51);">\d+$</font> → 结尾的数字
**<font style="color:rgb(51, 51, 51);">*</font>**匹配前一个字符0次或多次<font style="color:rgb(51, 51, 51);">a*</font><font style="color:rgb(51, 51, 51);">''</font>, <font style="color:rgb(51, 51, 51);">'aaa'</font>
**<font style="color:rgb(51, 51, 51);">+</font>**匹配前一个字符1次或多次<font style="color:rgb(51, 51, 51);">a+</font><font style="color:rgb(51, 51, 51);">'a'</font>, <font style="color:rgb(51, 51, 51);">'aaa'</font>
**<font style="color:rgb(51, 51, 51);">?</font>**匹配前一个字符0次或1次<font style="color:rgb(51, 51, 51);">a?</font><font style="color:rgb(51, 51, 51);">''</font>, <font style="color:rgb(51, 51, 51);">'a'</font>
**<font style="color:rgb(51, 51, 51);">{m,n}</font>**匹配前一个字符m到n次<font style="color:rgb(51, 51, 51);">a{2,3}</font><font style="color:rgb(51, 51, 51);">'aa'</font>, <font style="color:rgb(51, 51, 51);">'aaa'</font>
`****`或操作
**<font style="color:rgb(51, 51, 51);">()</font>**捕获分组<font style="color:rgb(51, 51, 51);">(\d+)</font> → 提取数字
记录一下跟菜鸟教程的学习过程 Python re 模块 | 菜鸟教程

更多推荐