定義宏,向前掃描上標和/或下標,「吸收」它們並移動它們的參數

定義宏,向前掃描上標和/或下標,「吸收」它們並移動它們的參數

我有很多數學宏,根據定義它們已經有上標和/或下標,即類似

\newcommand*{\mymathsym}{x^{\text{foo}}_{\text{bar}}}

在文字正文中,這些符號經常需要額外的上/下標。這意味著,作者必須記住將主符號放入一對 {} 大括號中,否則會出現雙上/下標錯誤。

\begin{equation}
  {\mymathsym}^{\text{extra}}
\end{equation}

額外的上標成為輔助上標,並且設置得稍高和稍小: 額外的上標 這有兩個缺點: a) 在特殊的應用領域中,從概念的角度來看,兩個上標處於相同的層次結構級別。換句話說,兩個上標實際上都應該打印為列表“foo,extra”,相反的順序“extra,foo”也同樣好。 b) 如果主上標和下標的長度非常不平衡,則將次上標設定得很遠,例如

\newcommand*{\mymathsymlong}{x^{\text{foo}}_{\text{very long foobar}}}

\begin{equation}
{\mymathsymlong}^{\text{extra}}
\end{equation}

產量 相隔較遠的上標

作為解決方法,我目前使用以下定義,該定義採用可選參數並將參數附加到內部上標:

\newcommand*{\mymathsymext}[1][]{x^{\text{foo}\if!#1!\else, #1\fi}_{\text{very long foobar}}}

(請注意,我知道該條件\if!#1!不是測試空參數的正確方法,因為如果參數擴展為 a ,它就會失敗!。但我認為您了解巨集的作用。)

它被用作

\begin{equation}
\mymathsymext \qquad\text{vs.}\qquad \mymathsymext[\text{extra}]
\end{equation}

然而 在此輸入影像描述 ,這有兩個主要缺點:a)\newcommand僅支援單一可選參數。因此,我需要在設計時決定最終是否需要附加上標或附加下標。我不能兩者都支持。 b) 使用者必須記住放置附加上/下標的不常見語法。

問題:

如何定義一個\mymathsymsuper巨集

  • 如果後跟上標字元^<tok> 和/或下標字元_<tok>,則向前掃描,每個下標字元後面跟著一個附加標記 <tok>
  • “吸收它們”,並且
  • 將 <tok> 移到其內部上標/下標的末尾,並用逗號分隔?

完整的 MWE:

\documentclass{article}

\usepackage[T1]{fontenc}
\usepackage{lmodern}
\usepackage[utf8]{inputenc}
\usepackage{amsmath}

\newcommand*{\mymathsym}{x^{\text{foo}}_{\text{bar}}}

\newcommand*{\mymathsymlong}{x^{\text{foo}}_{\text{very long foobar}}}

\newcommand*{\mymathsymext}[1][]{x^{\text{foo}\if!#1!\else, #1\fi}_{\text{very long foobar}}}

\begin{document}

Here, the author must know that \verb#\mymathsym# has already a super- and subscript and must remember to put the main symbol into a pair of \{\}-braces, otherwise a double sup-/subscript error occurs.
The extra superscript becomes a secondary superscript and it set slightly higher and smaller:
\begin{equation}
{\mymathsym}^{\text{extra}}
\end{equation}

If the primary sup- and subscript are very unbalanced in their length, the secondary subscript is set very far apart:
\begin{equation}
{\mymathsymlong}^{\text{extra}}
\end{equation}

This extended macro takes an optional argument and ``absorbs'' the extra superscript into the primary superscript:
\begin{equation}
\mymathsymext \qquad\text{vs.}\qquad \mymathsymext[\text{extra}]
\end{equation}
Still, the author must remember this ``unusual'' syntax and it only supports either an extra super- or subscript, bot not both.

\paragraph{Question:}
How does one define a macro \verb#\mymathsymsuper# that
\begin{itemize}
  \item scans ahead if it followed by a superscript character $\verb!^!\langle \mathit{token}_\text{sup}\rangle$ and/or subscript character $\verb!_!\langle \mathit{token}_\text{sub}\rangle$ each followed by an    additional token $\mathit{token}_\text{sup}$ and $\mathit{token}_\text{sub}$ resp.
  \item ``absorbs them'', and
  \item moves $\mathit{token}_\text{sup}$ and/or $\mathit{token}_\text{sub}$ to end of its internal sup-/subscript separated by a comma?
\end{itemize}

\end{document}

答案1

這是輕而易舉的xparse

\documentclass{article}
\usepackage{amsmath}
\usepackage{xparse}

\NewDocumentCommand{\mymathsym}{e{^_}}{%
  x^{\mathrm{foo}\IfValueT{#1}{,#1}}_{\mathrm{bar}\IfValueT{#2}{,#2}}%
}

\begin{document}

\begin{gather}
\mymathsym \\
\mymathsym^{\mathrm{extrasup}} \\
\mymathsym_{\mathrm{extrasub}} \\
\mymathsym^{\mathrm{extrasup}}_{\mathrm{extrasub}} \\
\mymathsym_{\mathrm{extrasub}}^{\mathrm{extrasup}}   
\end{gather}

\end{document}

在此輸入影像描述

使用e{^_}巨集向前尋找^or _(以任一順序)並指派#1給上標、#2下標。您可以測試是否存在\IfValueT(或\IfValueTF如果您想要對不存在的子/上標執行某些操作)。

相關內容