新闻中心
自定义分词器:解决Python CountVectorizer忽略数字符号问题

python的`countvectorizer`在默认分词时会忽略非字母数字字符,导致在处理如“+83”或“-193”这类带有正负号的数字字符串时,符号被丢弃。本文将详细介绍如何通过编写一个自定义的正则表达式分词器,并将其集成到`countvectorizer`中,以确保在构建词袋模型时,数字及其前缀符号(正负号)能够被完整保留,从而生成符合预期的特征名称。
理解CountVectorizer的默认分词行为
CountVectorizer是Scikit-learn库中用于将文本数据转换为词频矩阵(词袋模型)的关键工具。它通过fit_transform方法对文本进行分词、构建词汇表并计算
词频。然而,其默认的分词器(基于正则表达式r'(?u)\b\w\w+\b')旨在提取单词,通常会忽略非字母数字字符。这意味着,当遇到像+83或-193这样的字符串时,+和-这些符号会被视为分隔符或噪声而被丢弃,只留下纯数字83或193作为词汇表中的特征。
考虑以下数据框:
RepID, Txt 1, +83 -193 -380 +55 +901 2, -94 +44 +2892 -60 3, +7010 -3840 +3993
如果直接使用默认的CountVectorizer,我们期望的列名是+83, -193等,但实际输出的列名将是83, 193等,丢失了重要的符号信息。
解决方案:自定义分词器
为了解决CountVectorizer默认行为带来的问题,我们需要提供一个自定义的分词函数。这个函数将负责以我们期望的方式解析文本,确保带有正负号的数字被视为一个完整的词元(token)。
1. 创建自定义分词函数
我们将使用Python的re模块来构建一个正则表达式,该表达式能够识别并捕获带有可选正负号的数字。re.split()函数在这里非常有用,它可以根据正则表达式将字符串分割成列表,并且如果正则表达式包含捕获组(括号),那么匹配到的分隔符也会被包含在结果列表中。
import re
import pandas as pd
import numpy as np
from sklearn.feature_extraction.text import CountVectorizer
def custom_tokenizer(text):
"""
自定义分词器,用于将文本分割成词元,并保留数字前的正负号。
例如:"+83 -193" 会被分割为 ['+83', '-193']。
"""
# 正则表达式解释:
# ([+-]?\d+)
# - [+-]? : 匹配一个可选的 '+' 或 '-' 符号
# - \d+ : 匹配一个或多个数字
# 整个表达式作为一个捕获组,确保匹配到的符号和数字组合被保留为词元。
tokens = [token.strip() for token in re.split('([+-]?\d+)', text) if token.strip()]
return tokens在custom_tokenizer函数中,re.split('([+-]?\d+)', text)会根据匹配到的[+-]?\d+模式来分割文本。由于([+-]?\d+)是一个捕获组,所以匹配到的部分(即带有符号的数字)也会作为列表元素返回。[token.strip() for token in ... if token.strip()]确保移除了空字符串和多余的空白。
2. 将自定义分词器集成到CountVectorizer
创建了自定义分词器后,只需在初始化CountVectorizer时,通过tokenizer参数指定这个函数即可。
Mistral AI
Mistral AI被称为“欧洲版的OpenAI”,也是目前欧洲最强的 LLM 大模型平台
182
查看详情
def BOW_with_custom_tokenizer(df_column_series):
"""
使用自定义分词器生成词袋模型的数据框。
参数:
df_column_series (pd.Series): 包含文本数据的DataFrame列。
返回:
pd.DataFrame: 包含词袋模型结果的数据框,列名保留了数字的正负号。
"""
# 初始化CountVectorizer,并传入自定义分词器
CountVec = CountVectorizer(tokenizer=custom_tokenizer)
# 对文本数据进行拟合和转换
Count_data = CountVec.fit_transform(df_column_series)
# 将稀疏矩阵转换为密集数组,并指定数据类型以节省内存
Count_data = Count_data.astype(np.uint8)
# 创建Pandas DataFrame,列名为词汇表中的特征(已保留符号)
cv_dataframe = pd.DataFrame(
Count_data.toarray(),
columns=CountVec.get_feature_names_out(),
index=df_column_series.index
)
return cv_dataframe.astype(np.uint8)注意事项:
- CountVectorizer的tokenizer参数期望一个可调用对象(函数),该对象接收一个字符串并返回一个字符串列表。
- ngram_range等其他参数仍然可以根据需求进行设置。如果同时使用ngram_range和tokenizer,CountVectorizer会先通过tokenizer分词,然后基于这些词元生成n-gram。
完整示例
让我们使用之前的数据框来测试这个改进后的BOW函数。
# 导入必要的库
import pandas as pd
import numpy as np
import re
from sklearn.feature_extraction.text import CountVectorizer
# 自定义分词器函数
def custom_tokenizer(text):
tokens = [token.strip() for token in re.split('([+-]?\d+)', text) if token.strip()]
return tokens
# 改进的BOW函数
def BOW_with_custom_tokenizer(df_column_series):
CountVec = CountVectorizer(tokenizer=custom_tokenizer)
Count_data = CountVec.fit_transform(df_column_series)
Count_data = Count_data.astype(np.uint8)
cv_dataframe = pd.DataFrame(
Count_data.toarray(),
columns=CountVec.get_feature_names_out(),
index=df_column_series.index
)
return cv_dataframe.astype(np.uint8)
# 示例数据
data = {
'RepID': [1, 2, 3],
'Txt': ['+83 -193 -380 +55 +901', '-94 +44 +2892 -60', '+7010 -3840 +3993']
}
df = pd.DataFrame(data)
# 应用改进的BOW函数
result_df = BOW_with_custom_tokenizer(df['Txt'])
print(result_df)输出结果:
+2892 +3993 +44 +55 +7010 +83 +901 -193 -380 -3840 -60 -94 0 0 0 0 1 0 1 1 1 1 0 0 0 1 1 0 1 0 0 0 0 0 0 0 1 1 2 0 1 0 0 1 0 0 0 0 1 0 0
从输出可以看出,列名现在正确地包含了数字前的正负号,如+83、-193等,这正是我们期望的结果。
总结与扩展
通过为CountVectorizer提供一个自定义分词器,我们成功解决了其默认行为中忽略非字母数字字符的问题,尤其是在需要保留数字符号的场景下。这种方法不仅适用于处理数字符号,还可以推广到其他需要特殊分词规则的场景,例如:
- 特定格式的ID或编码: 如果文本中包含ABC-123或REF_XYZ等需要作为整体识别的字符串。
- 词形还原或词干提取: 在分词阶段集成nltk或spaCy等库的词形还原或词干提取功能。
- 过滤特定模式: 在分词时直接过滤掉不符合特定模式的词元。
- 复合词处理: 将某些由空格分隔但语义上紧密的词语(如“机器学习”)视为一个单一词元。
理解并掌握CountVectorizer的tokenizer参数的用法,极大地增强了其灵活性和适应性,使其能够满足更复杂的文本预处理需求。在实际应用中,根据数据的特点和分析目标,选择或设计合适的自定义分词器是构建高质量词袋模型的重要一步。
以上就是自定义分词器:解决Python CountVectorizer忽略数字符号问题的详细内容,更多请关注其它相关文章!
# 数据包
# 重庆网站关键词优化系统
# 酒店宣传网站建设教程
# 静海区市场营销推广方案
# 正规seo推广有哪些seo博客
# 天津网站建设制作流程
# 吴忠网站推广招聘
# ai智能推广营销策略
# 范文网站建设
# 怎样进行seo推广代做
# 怎么知道推广网站
# 如何将
# python
# 提供一个
# 可选
# 欧洲
# 也会
# 转换为
# 词汇表
# 自定义
# 工具
# 编码
# 正则表达式
相关栏目:
【
科技资讯46185 】
【
网络学院92790 】
相关推荐:
解决Flask中Quill编辑器内容提交失败及TypeError的指南
如何将一个大型PHP应用拆分为多个Composer包_微服务与模块化架构的Composer实践
优化LangChain文档加载与ChromaDB集成:解决多文档处理与分块问题
Surface怎么安装系统 微软Surface Pro U盘重装win11教程
漫蛙2网页版漫画入口 漫蛙漫画在线官方登录
win11专注助手在哪 Win11免打扰模式设置与自动化规则【指南】
Mac终端命令大全_Mac常用Terminal指令速查
Win10快速启动功能利弊分析 Win10开启或关闭快速启动教程【技巧】
从OpenAI API响应中高效提取生成文本
新手怎么开始学化妆 零基础化妆入门教程
怎么在浏览器上运行HTML文件_浏览器运行HTML文件技巧【技巧】
腾讯QQ邮箱官方网站_QQ邮箱网页版在线登录
mysql密码锁定怎么解锁_mysql密码锁定解锁后修改密码步骤
TikTok搜索不到用户发布内容怎么办 TikTok用户内容搜索优化方法
黑鲨3Pro怎样在相册开漫画风滤镜_iPhone黑鲨3Pro相册开漫画风滤镜【趣味滤镜】
痛风发作了怎么办? 快速止痛和后期饮食调理
c++ 获取系统当前时间 c++时间戳获取方法
QQ邮箱官方网站登录入口_QQ邮箱网页版在线使用
学习通网页版快速入口 学习通官网网页版直接打开
俄罗斯方块最新版入口 俄罗斯方块在线玩官网入口
火锅吃太多会怎样 火锅吃太多会上火吗
UE5.7引擎表现爆炸优化无敌!5090跑4K稳定60FPS
vivo浏览器自带的下载器速度慢怎么办 vivo浏览器提升文件下载速度的技巧
qq游戏手机版下载安装_qq游戏移动端入口
一加Ace 6T实拍样张首次公布!李杰:主摄实力完全看齐4K档性能旗舰
Excel组合图表怎么做 Excel创建柱状图与折线组合图教程【图表】
Go与Ruby之间实现AES加密互通:CFB模式下的密钥长度匹配策略
高德地图家和公司地址在哪设置 高德地图通勤路线设置方法【超详细】
怎么在html里运行vbs脚本_html中运行vbs脚本方法【教程】
如何使用Node.js csv 包按条件移除含空字段的CSV记录
Composer的 "licenses" 命令如何帮助你遵守开源协议_检查项目依赖的许可证合规性
微信网页版官方入口教程 微信网页版网页版快速登录步骤
sublime如何处理大型CSV文件的列对齐_sublime高级表格编辑插件指南
夸克浏览器网页版最新地址 夸克浏览器官方入口合集
mc.js游戏直达 mc.js网页免下载版本秒进地址
html5 app怎么运行环境_配html5 app运行环境【教程】
蓝湖怎样用切图标注提对接效率_蓝湖用切图标注提对接效率【设计对接】
css元素hover动画延迟生效怎么办_使用animation-delay调整触发时间
126邮箱账号注册 电脑版登录入口
AO3最新官网入口公告_2025AO3镜像站实时查询方法
支付宝解绑银行卡步骤_支付宝如何解除绑定银行卡
win11开机启动修复循环怎么办 Win11无法进入系统高级启动解决方法【修复】
b站赚钱渠道_b站收益来源
三星GalaxyZFold5怎样在相册制作折叠屏分镜_iPhone三星GalaxyZFold5相册制作折叠屏分镜【创意编辑】
深入理解J*aScript中的B样条曲线与节点向量生成
Golang如何通过reflect操作map_Golang reflect map操作与遍历技巧
深入理解Go语言中的指针类型:以*string为例
Kafka Streams中基于消息头条件过滤消息的实现指南
漫蛙2漫画入口 漫蛙正版网页漫画直达网址
css绝对定位元素脱离父容器怎么办_确保父元素position非static


2025-12-05
浏览次数:次
返回列表