- 人工智能
- 大模型
- 数据工程
- 数据清洗
- 数据增强
- 数据质检
【免费下载链接】data-juicer
Data processing for and with foundation models! 🍎 🍋 🌽 ➡️ ➡️🍸 🍹 🍷
导读
character_repetition_filter是 Data-Juicer 中用于文本质量清洗的核心 filter 算子之一:它按字符级 n-gram 统计每个样本的重复率,并只保留重复率落在指定区间内的样本,从而批量剔除「重复轰炸」(如连续复读同一片段)的低质文本。读完本文,你将掌握该算子的数学定义与源码级实现原理、rep_len/min_ratio/max_ratio三个核心参数的调参方法、在 YAML recipe 与 Python API 两种使用方式下的完整配置示例,以及它与word_repetition_filter的选型差异。
算子概览:定位与适用场景
在 Data-Juicer 的算子体系中,character_repetition_filter属于filter(过滤)类型,算子注册名为character_repetition_filter,标签为cpu, text,即纯 CPU 文本算子,不依赖任何模型与 GPU。官方文档 character_repetition_filter.md 对其核心职责的表述是:计算每个样本的字符级 n-gram 重复率(character-level n-gram repetition ratio),并过滤掉不在指定范围内的样本;关键指标char_rep_ratio会被缓存进样本的stats字段。
该算子最常见的应用场景:
- 剔除模型训练语料中的复读、口水话、重复拼接的文本;
- 在清洗流程中与其他文本质量过滤器(如
alphanumeric_filter、word_repetition_filter、perplexity_filter)组合,构成多层次的文本质检链路。
从源码看,本算子的算法实现参考了 HuggingFace 的 text-data-filtering 头注释),属于业界常用的重复率清洗方法在 Data-Juicer 中的工程化落地。
参数配置:三个核心参数与扩展参数
算子参数在 character_repetition_filter.md 的「Parameter Configuration」一节有完整表格,结合源码 character_repetition_filter.py 的构造函数可一一对应:
| 参数名 | 类型 | 默认值 | 含义 |
|---|---|---|---|
rep_len | int(要求 > 0,即PositiveInt/Gt(gt=0)) | 10 | 字符级 n-gram 的窗口长度 n,即每个待统计的 n-gram 包含的字符数 |
min_ratio | float | 0.0 | 重复率下限,样本char_rep_ratio低于此值则被过滤 |
max_ratio | float | 0.5 | 重复率上限,样本char_rep_ratio超过此值则被过滤 |
args/kwargs | - | '' | 透传给基类Filter/OP的扩展参数(如batch_size、text_key、num_proc等) |
需要说明的是,args/kwargs实际接收的是 Data-Juicer 算子基类 base_op.py 中定义的全部通用参数,主要包括:
- 数据键:
text_key(默认"text",指定待处理的文本字段)、image_key、video_key等; - 执行策略:
batch_size(默认 1000)、num_proc(默认 -1,自动计算并发度)、skip_op_error(默认 False,是否跳过单样本异常)、auto_op_parallelism; - Ray 相关:
num_cpus、num_gpus、memory、runtime_env等。
另外,所有 filter 算子还继承了基类的三个过滤语义参数(见 base_op.py):
min_closed_interval(默认 True):下限是否为闭区间(>= min_ratio而非> min_ratio);max_closed_interval(默认 True):上限是否为闭区间(<= max_ratio而非< max_ratio);reversed_range(默认 False):是否反转过滤区间,即只保留落在区间之外(< min_ratio或> max_ratio)的样本。
参数取值的实战建议
rep_len控制重复检测的"粒度":窗口越大,只有足够长的连续重复片段才会被记为重复,误伤率越低;窗口过小(如 2~3)会把正常文本中偶然出现的短字符串重复也计入重复率,导致误过滤。默认值 10 是兼顾灵敏度与准确率的经验取值。max_ratio是调节严格程度的关键旋钮:默认 0.5 意味着重复 n-gram 频次贡献占总 n-gram 频次一半以上的样本会被剔除;调低更严格、调高更宽松。对于聊天记录、对话类数据建议放宽,对于网页抓取、OCR 文本建议收紧。
核心原理:重复率char_rep_ratio的精确计算方式
重复率指标char_rep_ratio的名字定义在 constant.py 的StatsKeysConstant中,与word_rep_ratio(词级重复率)等指标并列。它的完整计算过程实现在 character_repetition_filter.py 的compute_stats_batched方法中,分为四步:
第 1 步:统计所有字符 n-gram 的频次。对文本cur_text,以self.n(即rep_len)为窗口做滑窗:
freq_char_ngrams = {} for i in range(len(cur_text) - self.n + 1): char_ngram = cur_text[i : i + self.n] freq_char_ngrams[char_ngram] = freq_char_ngrams.get(char_ngram, 0) + 1这里中英文一视同仁:文档效果演示中明确指出「中文也是一个字算一个长度」,即一个汉字算一个字符、参与滑窗统计。
第 2 步:处理过短文本。若文本长度小于 n,滑窗一个 n-gram 都产生不了,freq_char_ngrams为空,此时重复率直接记为0.0(不会被误判为重复)。
第 3 步:确定「重复 n-gram」的集合。将频次降序排列后:
num_no_rep_char_ngrams = freq_char_ngrams.count(1) # 只出现 1 次的 n-gram 数量 num_rep_char_ngrams = min( int(np.sqrt(len(freq_char_ngrams))), # 取 n-gram 种类数的平方根 len(freq_char_ngrams) - num_no_rep_char_ngrams, # 且不超过“出现不止一次”的种类数 )重复 n-gram 被定义为:频次降序排列后,取前sqrt(种类数)个(且这些 n-gram 必须出现超过 1 次)。这一设计借鉴了长尾分布假设——正常情况下绝大多数 n-gram 只出现一次,只有真正重复的 n-gram 才会高频出现,用平方根截断可以避免把低频正常片段也算进重复集合。
第 4 步:计算重复率。重复 n-gram 的频次之和占总频次(即文本中所有 n-gram 的出现总次数)的比例:
total = sum(freq_char_ngrams) char_rep_ratio = sum(freq_char_ngrams[:num_rep_char_ngrams]) / total if total != 0 else 0.0因此char_rep_ratio的取值范围是[0.0, 1.0]:完全没有重复的文本为 0.0,全文只有单一字符反复出现的极端文本接近 1.0。这一点被单元测试 test_character_repetition_filter.py 直接验证:25 个a组成的文本重复率> 0.9,26 个互不重复字母组成的文本重复率恰为0.0。
缓存与复用机制
compute_stats_batched开头会检查该样本的stats字段中是否已有char_rep_ratio:若已存在则直接跳过重算(character_repetition_filter.py)。这意味着:
- 同一算子重复执行不会覆盖已算好的统计值(测试 test_compute_stats_batched_skips_existing 验证了预计算的
0.42会被原样保留); - 该指标可以被其他算子或分析模块复用,例如 Data-Juicer 的统计分析工具会读取
StatsKeys.char_rep_ratio展示重复率分布(参见 app.py 中该指标与可视化效果的绑定)。
过滤判定:区间比较与基类语义
统计完成后,过滤判定由process_batched完成(character_repetition_filter.py):
return map( lambda stat: self.get_keep_boolean(stat[StatsKeys.char_rep_ratio], self.min_ratio, self.max_ratio), samples[Fields.stats], )get_keep_boolean定义在基类 base_op.py,它完整实现了前面提到的区间语义:
- 默认(闭区间)下,保留条件为
min_ratio <= ratio <= max_ratio; - 若设置
min_closed_interval=False,下限变为开区间(> min_ratio); - 若设置
max_closed_interval=False,上限变为开区间(< max_ratio); - 若设置
reversed_range=True,上述比较结果整体取反,即只保留不在区间内的样本。
注意本算子_batched_op = True(character_repetition_filter.py),因此实际执行走的是批处理路径:compute_stats_batched一次处理一个 batch 的所有样本,process_batched返回一组布尔标志。整个算子在执行器中的调用链为:Filter.run→ 先dataset.map(compute_stats)缓存统计值 → 再dataset.filter(process)剔除样本(见 base_op.py),两个阶段都支持num_proc多进程并行。此外,Data-Juicer 的 tracer 机制会在过滤阶段记录被剔除的样本,用于后续的数据质量审计(见 base_op.py 的wrap_filter_with_tracer)。
效果演示:官方示例的逐步拆解
官方文档 character_repetition_filter.md 给出的效果演示采用如下配置:
CharacterRepetitionFilter(rep_len=5, min_ratio=0.0, max_ratio=0.4, batch_size=2)即统计 5-gram 重复率,只保留重复率落在[0.0, 0.4]的样本。四组输入样本与过滤结果为:
| 输入样本 | 结果 |
|---|---|
Today is Sund Sund Sund Sund Sund Sunda and it's a happy day! | ❌ 剔除(5-gram 重复率 > 0.4) |
a v s e c s f e f g a a a a a a a a a a | ❌ 剔除(大量重复的a,5-gram 重复率 > 0.4) |
,。、„”“«»1」「《》´∶:?!();–—.~’…━〈〉【】%► | ✅ 保留 |
中文也是一个字算一个长度 | ✅ 保留 |
其中第 3 条样本虽然全是标点符号,但互不重复,因此重复率为 0,落在区间内被保留;第 4 条中文样本验证了「一个汉字算一个字符」的统计口径。
该示例与单元测试 test_case 完全一致,测试通过NestedDataset构造数据集、先map(op.compute_stats)再filter(op.process)复现了完整过滤流程,可作为自行验证算子的最小可运行样例。
实战配置:在 Data-Juicer recipe 中接入该算子
Data-Juicer 推荐通过 YAML recipe 声明式地组织处理流程。在 recipe 中,character_repetition_filter作为process列表的一员出现。官方配置模板 config_all.yaml 中的默认写法为:
process: - character_repetition_filter: # filter text with the character repetition ratio out of specific range rep_len: 10 # repetition length for char-level n-gram min_ratio: 0.0 # the min ratio of filter range max_ratio: 0.5 # the max ratio of filter range实际 demo 配置 demo.yaml 也采用了完全相同的默认参数组合,并且把它放在alphanumeric_filter、average_line_length_filter之后、flagged_words_filter、language_id_score_filter之前,可见它通常作为通用文本质量过滤链路的中段环节。完整的 recipe 运行方式如下:
# 命令行运行(先安装>project_name: 'demo' dataset_path: './demos/data/demo-dataset.jsonl' # 输入数据集 np: 4 # 子进程数 export_path: './outputs/demo/demo-processed.jsonl' process: - character_repetition_filter: # 字符级重复率过滤 rep_len: 10 min_ratio: 0.0 max_ratio: 0.5如果你希望更严格地剔除复读文本,可以把max_ratio调到0.3并适当缩小rep_len(如 6);反之,如果只是轻量清洗,保持默认即可。值得注意的是,Data-Juicer 支持对 filter 类算子做算子融合优化:word_repetition_filter注册了INTER_WORDS中间变量用于词切分复用(见 word_repetition_filter.py),因此将字符级与词级重复率过滤串联使用时,Data-Juicer 会尽量复用中间计算结果以提升吞吐。
与 word_repetition_filter 的选型对比
Data-Juicer 同时提供字符级(本算子)与词级(word_repetition_filter)两种重复率过滤器,二者共享相同的参数结构(rep_len/min_ratio/max_ratio,默认值均为 10 / 0.0 / 0.5),但在统计单元与实现上有本质区别:
| 维度 | character_repetition_filter | word_repetition_filter |
|---|---|---|
| 统计单元 | 连续字符组成的 n-gram | 词(word)组成的 n-gram |
| 是否需要分词 | 否,直接滑窗 | 是,默认按空白分词,tokenization=True时使用 sentencepiece 模型(需指定lang) |
| 预处理 | 无 | 小写化、去特殊字符(words_refinement) |
| 典型捕获目标 | 字符级复读、aaaaa...式无意义填充 | 词语级复读、重复的短语/句子模式 |
选择建议:处理字母堆积、乱码填充、标点轰炸类问题选字符级;处理整句整段复读类问题,词级往往语义更直观。两者都继承Filter基类,也都缓存各自的统计指标(char_rep_ratio/word_rep_ratio),可放心在同一 recipe 中组合使用。
测试与验证:如何确认算子行为
该算子的行为在仓库中有系统化的单元测试覆盖,文件为 test_character_repetition_filter.py,除官方效果演示对应的test_case外,还包含:
test_existing_stats:已缓存char_rep_ratio的样本不会被重算;test_compute_stats_batched_directly:高度重复文本重复率 > 0.9、完全无重复文本重复率 = 0.0;test_process_batched_directly:0.9 / 0.2 / 0.0三个比值在[0.0, 0.4]区间下分别得到False / True / True的保留标志;test_compute_stats_batched_short_text:短于rep_len的文本(含空串)重复率恒为 0.0;test_compute_stats_batched_mixed_repetition:中等重复文本重复率 > 0,无重复文本重复率为 0。
运行测试验证行为:
python -m pytest tests/ops/filter/test_character_repetition_filter.py -v若想在自有数据上观察该算子的实际统计值,可先运行compute_stats阶段并把stats_export_path指向输出文件(该参数由Filter基类提供,见 base_op.py),导出的统计文件会包含每条样本的char_rep_ratio,方便你据此调整min_ratio/max_ratio阈值。
小结
character_repetition_filter是 Data-Juicer 文本质量过滤家族中一个实现精简、语义清晰的基础算子:通过「字符 n-gram 频次统计 + 平方根截断确定重复集合」的方式得到char_rep_ratio指标,再以区间比较完成过滤。它的工程化亮点包括批处理执行、统计值缓存复用、多进程并行、tracer 审计以及与词级过滤器的中间结果复用。对于任何需要控制语料文本重复度、提升数据信噪比的清洗 pipeline,它都是一块高性价比的基石组件。
延伸阅读:算子全览见 Operators.md;与词级版本对比见 word_repetition_filter.py;过滤算子的通用区间语义(开闭区间、反转区间)见基类 base_op.py;官方默认 recipe 配置见 config_all.yaml。
- 人工智能
- 大模型
- 数据工程
- 数据清洗
- 数据增强
- 数据质检
【免费下载链接】data-juicer
Data processing for and with foundation models! 🍎 🍋 🌽 ➡️ ➡️🍸 🍹 🍷
相关推荐
DLSS Swapper 完整上手指南:从安装到切换游戏 DLSS 版本
DLSS Swapper 完整上手指南:从安装到切换游戏 DLSS 版本 游戏自带的 DLSS 版本停留在旧版,画面表现一般,开发者却迟迟不更新。DLSS Sw
人工智能大模型数据工程数据清洗数据增强数据质检Reactotron 桌面应用 3.x 演进全解析:从 Timeline 深度搜索到 MCP 与敏感数据脱敏
Reactotron 桌面应用 3.x 演进全解析:从 Timeline 深度搜索到 MCP 与敏感数据脱敏 Reactotron 是一款用于检视 React
人工智能大模型数据工程数据清洗数据增强数据质检EUI Docusaurus 主题 2026 年演进实录:交互、图标与 Demo 能力的全面升级
EUI Docusaurus 主题 2026 年演进实录:交互、图标与 Demo 能力的全面升级 本篇技术指南以 @elastic/eui docusaurus
人工智能大模型数据工程数据清洗数据增强数据质检
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考