You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Vue JS段落术语替换异常:误处理解释文本中的词汇

术语替换时误匹配解释文本的问题修复

问题背景

我要把文章里属于术语表的特定词汇,替换成包裹在glossary_container类里的原词汇,同时在旁边加个可点击的+按钮展示术语解释,但现有代码出现了异常:

问题示例

术语表内容:

  • tree:"hello I am a tree and a branch and I am green"
  • flower:"hello I am flower"
  • branch:"hello I am branch"

文章原文:"tree has many things, such as a flower,a branch"
预期效果:tree、flower、branch旁边都显示+按钮
实际异常:tree的解释文本里的"branch"被误替换,导致HTML结构错乱,页面显示出问题

问题根源

代码会扫描已经添加了解释框的内容,把解释文本里的术语当成原文内容进行替换了,必须只基于原始文章内容执行替换操作。

当前使用的Vue代码

const content = this.isRtl ? this.post.content_ar : this.post.content_en
let modifiedContent = content.replaceAll(/<br(\s*\/)?>/gi, '<br /><br />');

// Loop through each glossary term
this.glossaries.forEach((glossary, index) => {
const title = this.isRtl ? glossary.title_ar : glossary.title_en
const desc = this.isRtl ? glossary.desc_ar : glossary.desc_en
let filteredDesc = desc.replaceAll(/[\"']/g, '');
    // Check if the glossary term exists in the content
    if (content.includes(title)) {
        console.log('content');
        // Replace the glossary term with a span containing the term and plus sign
        modifiedContent = modifiedContent.replace(
            title,
            `<span class="glossary_container"><span>${title}</span><span class="plus-sign" data-index="${index}" data-title="${filteredDesc}" style="cursor:pointer">+</span></span>`
        );
    }
});
return modifiedContent;

修复方案

核心思路是全程基于原始文章内容做匹配替换,绝对不能在已经插入过解释框的HTML内容上反复操作。下面提供两种可行方案:

方案一:一次性批量替换(推荐)

用正则表达式一次性匹配所有术语,避免循环中修改已被替换的内容:

const content = this.isRtl ? this.post.content_ar : this.post.content_en
let modifiedContent = content.replaceAll(/<br(\s*\/)?>/gi, '<br /><br />');

// 提取所有术语标题,转义正则特殊字符防止语法冲突
const termTitles = this.glossaries.map(glossary => {
  const title = this.isRtl ? glossary.title_ar : glossary.title_en;
  return title.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
});
// 构建匹配单词边界的正则,避免部分匹配(比如不会把"branches"里的"branch"当成术语)
const termRegex = new RegExp(`\\b(${termTitles.join('|')})\\b`, 'g');

// 一次性替换所有匹配到的术语
modifiedContent = modifiedContent.replace(termRegex, (matchedTerm) => {
  // 找到匹配术语对应的 glossary 项
  const glossary = this.glossaries.find(g => {
    return this.isRtl ? g.title_ar === matchedTerm : g.title_en === matchedTerm;
  });
  if (!glossary) return matchedTerm;

  const desc = this.isRtl ? glossary.desc_ar : glossary.desc_en;
  const filteredDesc = desc.replaceAll(/[\"']/g, '');
  const index = this.glossaries.indexOf(glossary);

  return `<span class="glossary_container"><span>${matchedTerm}</span><span class="plus-sign" data-index="${index}" data-title="${filteredDesc}" style="cursor:pointer">+</span></span>`;
});

return modifiedContent;

方案二:占位符中转法

如果想保留原来的循环逻辑,可以先用唯一占位符替换原始内容里的术语,最后再把占位符换成带按钮的HTML:

const content = this.isRtl ? this.post.content_ar : this.post.content_en
let modifiedContent = content.replaceAll(/<br(\s*\/)?>/gi, '<br /><br />');

const replaceMap = new Map();

this.glossaries.forEach((glossary, index) => {
  const title = this.isRtl ? glossary.title_ar : glossary.title_en;
  const desc = this.isRtl ? glossary.desc_ar : glossary.desc_en;
  const filteredDesc = desc.replaceAll(/[\"']/g, '');

  if (content.includes(title)) {
    // 生成唯一占位符,避免替换时互相干扰
    const placeholder = `__GLOSSARY_TERM_${index}__`;
    // 先把原始内容里的术语换成占位符
    const escapedTitle = title.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
    modifiedContent = modifiedContent.replace(new RegExp(`\\b${escapedTitle}\\b`, 'g'), placeholder);
    // 记录占位符对应的最终HTML
    replaceMap.set(placeholder, `<span class="glossary_container"><span>${title}</span><span class="plus-sign" data-index="${index}" data-title="${filteredDesc}" style="cursor:pointer">+</span></span>`);
  }
});

// 最后统一替换占位符为实际HTML
replaceMap.forEach((html, placeholder) => {
  modifiedContent = modifiedContent.replaceAll(placeholder, html);
});

return modifiedContent;

关键注意点

  • 两种方案都确保只处理原始文章里的术语,不会碰解释文本里的内容
  • 用\b单词边界正则,防止误匹配包含术语的长单词(比如"branching")
  • 必须转义术语里的正则特殊字符(如$、(、.等),否则会导致正则失效

内容的提问来源于stack exchange,提问作者Israa Elaiwa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.24 11:42:03