这个问题是我试图解决主要问题(MWE 在那里)。
我意识到使用宏
\newcommand{\veca}{|_{\vec{a}}}
next to\bigg
被视为单个 token,因此这两个查询具有相同的输出
\bigg\veca
\bigg{|_{\vec{a}}}
我不知道如何定义\veca
它首先被扩展的方式,所以我尝试重新定义,\bigg
以便第二个参数总是扩展一次
我查阅了一下,amsmath.sty
发现所有\big
、\Big
、都是使用 定义的:\bigg
\Bigg
\bBigg@
\renewcommand{\big}{\bBigg@\@ne}
\renewcommand{\Big}{\bBigg@{1.5}}
\renewcommand{\bigg}{\bBigg@\tw@}
\renewcommand{\Bigg}{\bBigg@{2.5}}
\ifx\leavevmode@ifvmode\@undefined
\def\bBigg@#1#2{%
{\@mathmeasure\z@{\nulldelimiterspace\z@}%
{\left#2\vcenter to#1\big@size{}\right.}%
\box\z@}}
\else
\def\bBigg@#1#2{\leavevmode@ifvmode
{\@mathmeasure\z@{\nulldelimiterspace\z@}%
{\left#2\vcenter to#1\big@size{}\right.}%
\box\z@}}
\fi
以下是我尝试使用以下方法实现扩展expl3
\documentclass{article}
\usepackage{amsmath}
\newcommand{\veca}{|_{\vec{a}}}
\makeatletter
\ExplSyntaxOn
\cs_set_eq:NN \better_big:nn \bBigg@
\cs_generate_variant:Nn \better_big:nn {no}
\cs_set:Npn \bBigg@ #1#2 {
\better_big:no #1 #2
}
\ExplSyntaxOff
\makeatother
\begin{document}
\[
\frac{f(\vec{x})}{g(\vec{x})}\bigg\veca \qquad
\frac{f(\vec{x})}{g(\vec{x})}\bigg|_{\vec{a}}
\]
\end{document}
任何建议都非常感谢。纯 LaTeX2 解决方案也非常受欢迎。
答案1
您几乎已经完成了。但是 o 型扩展默认会为结果加上括号,因此您需要一个不带括号的扩展。
\documentclass{article}
\usepackage{amsmath}
\newcommand{\veca}{|_{\vec{a}}}
\makeatletter
\ExplSyntaxOn
\cs_set_eq:NN \better_big:nn \bBigg@
\cs_set:Npn \bBigg@ #1#2 {
\exp_last_unbraced:Nno \better_big:nn {#1} {#2}
}
\ExplSyntaxOff
\makeatother
\begin{document}
\[
\frac{f(\vec{x})}{g(\vec{x})}\bigg\veca \qquad
\frac{f(\vec{x})}{g(\vec{x})}\bigg|_{\vec{a}}
\]
\end{document}
请注意的 o 扩展#2
必须是括号平衡的。
请注意,这将破坏其他一些用法,例如参见评论。我认为解决此问题的一种方法是测试内部宏是否是“想要扩展”的宏,例如
\cs_set:Npn \bBigg@ #1#2 {
\tl_if_eq:nnTF {#2} {\veca} {
\exp_last_unbraced:Nno \better_big:nn {#1} {#2}
}
{
\better_big:nn {#1} {#2}
}
}
(看,TeX 不是魔法。然后如果你想要某个系统将宏标记为“是否要扩展”,你可以定义一些辅助宏等。它很快变得复杂。functional
包做了一些类似的事情来查看参数中的内部宏是否“是一个函数”)