MathJax与Markdown下划线冲突问题的简易解决方法
解决Jekyll(AcademicPages)中数学表达式下划线渲染异常问题
问题说明
使用Jekyll的AcademicPages主题搭建站点时,页面包含大量数学表达式,由于Markdown与Jekyll的渲染逻辑冲突,导致公式中的下划线显示异常:
- 直接使用
_时,正文段落里的下划线会被Markdown解析为斜体标记,公式格式错乱 - 手动转义为
\_时,列表项和数学环境中的下划线仍无法正常渲染
因页面篇幅较大,手动逐个转义下划线不现实,需要无需手动操作的解决方案。
已尝试的无效方法
- 在正文首尾添加
{% raw %}和{% endraw %},页面无任何变化 - 为
$...$形式的行内公式添加<span>标签,仅修复文本格式,数学表达式下划线依然丢失 - 为
$...$形式的行内公式添加<div>标签,无任何效果
可行解决方案
1. 调整Kramdown渲染配置
AcademicPages默认使用Kramdown作为Markdown渲染器,修改_config.yml配置,让Kramdown忽略数学环境中的下划线解析:
kramdown: math_engine: mathjax parse_block_html: true parse_span_html: true auto_ids: false enable_coderay: false syntax_highlighter: rouge # 配置MathJax优先解析公式 math_engine_opts: preview: true
同时确认站点已加载MathJax,可检查_includes/head.html中是否包含类似脚本:
<script src="https://cdn.jsdelivr.net/npm/mathjax@3/es5/tex-mml-chtml.js"></script>
2. 自定义Liquid标签包裹数学表达式
创建Jekyll插件,用自定义标签包裹数学内容,避免Markdown解析下划线:
- 在站点根目录创建
_plugins/math_tag.rb文件,写入代码:
module Jekyll class MathBlockTag < Liquid::Block def render(context) content = super "$$#{content.strip}$$" end end class MathInlineTag < Liquid::Tag def initialize(tag_name, markup, tokens) super @markup = markup.strip end def render(context) "$#{@markup}$" end end end Liquid::Template.register_tag('math', Jekyll::MathBlockTag) Liquid::Template.register_tag('math_inline', Jekyll::MathInlineTag)
- 在Markdown文件中替换原有数学环境:
- 行内公式:
{% math_inline \operatorname{ext}_\in(X) = \operatorname{ext}_\in(\emptyset) %} - 块级公式:
{% math %} \operatorname{ext}_\in(X) = \operatorname{ext}_\in(\emptyset) {% endmath %}
3. 批量预处理Markdown文件
用脚本批量处理所有Markdown文件,自动转义数学环境内的下划线:
import re import os def fix_math_underscores(file_path): with open(file_path, 'r', encoding='utf-8') as f: content = f.read() # 处理块级公式 $$...$$ content = re.sub(r'\$\$(.*?)\$\$', lambda m: '$$' + m.group(1).replace('_', r'\_') + '$$', content, flags=re.DOTALL) # 处理行内公式 $...$ content = re.sub(r'\$(.*?)\$', lambda m: '$' + m.group(1).replace('_', r'\_') + '$', content) with open(file_path, 'w', encoding='utf-8') as f: f.write(content) # 遍历当前目录下所有markdown文件 for root, dirs, files in os.walk('.'): for file in files: if file.endswith('.md'): fix_math_underscores(os.path.join(root, file))
注意:运行脚本前请备份所有Markdown文件,避免误替换。
内容的提问来源于stack exchange,提问作者Clement Yung
相关产品推荐
相关产品推荐

