36 lines
1.3 KiB
JavaScript
36 lines
1.3 KiB
JavaScript
// =============================================================================
|
|
// 中文轻量分词工具(不依赖第三方分词库)
|
|
// 用「字符 bigram」做特征提取,兼顾关键词统计与相似度计算
|
|
// 复用方:reply-quality.mjs(关联度)、bot-persona.mjs(立场关键词)
|
|
// =============================================================================
|
|
|
|
// 高频虚词/停用字(单字)。bigram 两端都是停用字时视为无意义片段。
|
|
const STOP_CHARS = new Set(
|
|
(
|
|
"的了是在和与或也都就不没要我你他她它们这那有为到对及等把被从向以其之于上下里外中" +
|
|
"啊吗呢吧嗯哦哈啦嘿唉真应该可能觉得认为什么怎么为什么个些这个那个"
|
|
).split("")
|
|
);
|
|
|
|
function isMeaningfulGram(gram) {
|
|
const [a, b] = gram;
|
|
return !(STOP_CHARS.has(a) && STOP_CHARS.has(b));
|
|
}
|
|
|
|
/**
|
|
* 将中文文本切分为 bigram 词元列表。
|
|
* 英文/数字保留原样参与切分,标点与空白被剔除。
|
|
* @param {string} text
|
|
* @returns {string[]}
|
|
*/
|
|
export function tokenize(text) {
|
|
if (!text) return [];
|
|
const cleaned = String(text).replace(/[^\u4e00-\u9fa5a-zA-Z0-9]+/g, "");
|
|
const grams = [];
|
|
for (let i = 0; i < cleaned.length - 1; i++) {
|
|
const gram = cleaned.slice(i, i + 2);
|
|
if (isMeaningfulGram(gram)) grams.push(gram);
|
|
}
|
|
return grams;
|
|
}
|