Angular中如何用正则解析Markdown文件并转换为指定结构对象
实现代码
this.http.get('path/to/file.md',{responseType: 'text'}).subscribe(res => { // 统一换行符,消除不同系统换行差异 const normalizedText = res.replace(/\r\n|\r/g, '\n').trim(); const result = []; // 第一步:收集所有一级标题(## 包裹)的位置和内容 const h2Regex = /^##\s+(.*?)\s+##$/gm; let h2Match; const h2Positions = []; while ((h2Match = h2Regex.exec(normalizedText)) !== null) { h2Positions.push({ title: h2Match[1], startIndex: h2Match.index, endIndex: h2Match.index + h2Match[0].length }); } // 遍历处理每个一级标题对应的内容块 for (let i = 0; i < h2Positions.length; i++) { const currentH2 = h2Positions[i]; const nextH2 = h2Positions[i + 1]; // 截取当前一级标题到下一个一级标题之间的内容 const blockContent = normalizedText.slice( currentH2.endIndex, nextH2 ? nextH2.startIndex : undefined ).trim(); // 第二步:拆分内容块内的二级标题和对应正文 const h3List = []; const h3Regex = /^###\s+(.*?)\s+###\s*\n(.*?)(?=\n###|\n##|$)/gms; let h3Match; while ((h3Match = h3Regex.exec(blockContent)) !== null) { h3List.push({ title: h3Match[1].trim(), text: h3Match[2].trim() }); } // 组装目标结构 result.push({ heading1: currentH2.title, heading2: h3List }); } // 最终输出的result就是要求的结构 console.log(result); });
关键说明
- 分两次匹配的逻辑比单条复杂正则更易维护和调试,也能避免匹配边界错误
- 正则用了
m(多行匹配)和s(dotAll模式,允许.匹配换行符)标志,简化多行内容的匹配逻辑 - 用先行断言
(?=\n###|\n##|$)控制正文的截取边界,刚好到下一个二级标题/一级标题/文本末尾截止,不会多截取内容
兼容提示
如果运行环境不支持正则s修饰符,可将二级标题正则里的(.*?)替换为([\s\S]*?),效果完全一致。
内容的提问来源于stack exchange,提问作者banz
相关产品推荐
相关产品推荐

