函数参数不丢失括号

函数参数不丢失括号

这个 MWE 被简化得太多,以至于代码失去了实用性。然而,代码仍然表现出我遇到的问题。

\documentclass{article}
\usepackage{pgffor}
\usepackage{etoolbox}

\makeatletter
\newcommand\aetest[1]{%%
  \foreach \myl  in {#1}
    {%%
      \expandafter\ae@parse@line\myl
    }%% 
}

%% read the next character and                
%% branch off if its "*"                      
\def\ae@parse@line{%%
  \@ifnextchar*
  {\s@ae@parse@line}
  {\@ae@parse@line[]}}

%% what to do if there is no "*"              
\def\@ae@parse@line[#1]#2#3{%%
  \fbox{Case #2}\hspace*{0.5em}%%
  \def\ae@tmp{#3}%%
  \typeout{==[base case][#2]==>\expandonce\ae@tmp}%%
  \@ae@parse@content#3\@nil
}

%% If there's  "*" the command now            
%% expects three arguments with the argument  
%% #3 dressed up like an optional argument.   
%% After processing, pass arguments back to   
%% "\@ae@parse@line"                          
\def\s@ae@parse@line*#1#2[#3]{%%
  \def\ae@tmp{#2}%%
  \typeout{==[star case]___==>\expandonce\ae@tmp}%%
  \@ae@parse@line[#3]{#1}{#2}}

%% the "content" argument                     
%% may start with "[" which                   
%% signals that the "content"                 
%% should go in a `minipage`.                 
\def\@ae@parse@content{%%
  \@ifnextchar[%%]
  {\@ae@parse@mp}
  {\@@ae@parse@content}}

%% formatting for "non-minipage" case         
\def\@@ae@parse@content#1\@nil{%%
  \textbf{#1}\par}

%% formatting for "minipage" case             
\def\@ae@parse@mp[#1]#2\@nil{%%
  \fbox{\begin{minipage}[t]{#1}
    #2
  \end{minipage}}\par}

\makeatother

\begin{document}

\aetest{
  {A}{formatted correctly},
 *{B} {formatted correctly}[],
 *{C} {[4in] spurious space, and is \textbf{not} correct formatted}[],
 *{D}{[4in] no spurious space and correctly formatted}[],
  {E} {[2in] spurious space but still correctly formatted},
  {F}{[3in] no spurious space, formatted correctly},
  {G} {done as expected}}

\end{document}

生产

在此处输入图片描述

我感到好奇的是为什么 caseC格式不正确,而 caseE却正确。在我看来,如果它们都存在相同的虚假空格,那么我希望它们得到类似的处理。

查看log文件发现,在caseB和中空格被解析为参数的一部分,因此括号不会丢失。但是为什么在case和C中括号会消失呢?EG

这是日志文件的相关部分。==>指向传递的参数的内容并显示虚假空格和括号。

==[base case][A]==>formatted correctly
==[star case]___==> {formatted correctly}
==[base case][B]==> {formatted correctly}
==[star case]___==> {[4in] spurious space, and is \textbf {not} correct formatted}
==[base case][C]==> {[4in] spurious space, and is \textbf {not} correct formatted}
==[star case]___==>[4in] no spurious space and correctly formatted
==[base case][D]==>[4in] no spurious space and correctly formatted
==[base case][E]==>[2in] spurious space but still correctly formatted
==[base case][F]==>[3in] no spurious space, formatted correctly
==[base case][G]==>done as expected

答案1

#2中的参数\s@ae@parse@line被分隔(用 分隔[),因此 TeX 在查找它时不会跳过空格。并且,在 C 的情况下,初始空格会阻止括号剥离。

使用两个步骤:

%% If there's  "*" the command now
%% expects three arguments with the argument
%% #3 dressed up like an optional argument.
%% After processing, pass arguments back to
%% "\@ae@parse@line"
\def\s@ae@parse@line*#1#2{%
  \s@ae@parse@line@aux{#1}{#2}%
}
\def\s@ae@parse@line@aux#1#2[#3]{%
  \def\ae@tmp{#2}%%
  \typeout{==[star case]___==>\expandonce\ae@tmp}%%
  \@ae@parse@line[#3]{#1}{#2}}

以这种方式论证#2将正确地丢失括号,并且不会出现空格问题,因为 TeX 在寻找时会忽略它们未限定參數。

我没有改变任何其他东西,所以图像并不能反映真实情况。;-)

无论如何,如果你在尾随可选参数之前留一个空格,你就会得到相同的结果,就像

 *{C} {[4in] spurious space, and is \textbf{not} correct formatted} []% <-- a space!

在此处输入图片描述

答案2

按照@egreg的建议,我想出了以下方法来处理有害的、虚假的空白:

\def\s@ae@parse@line*#1#2{%%
  \def\ae@tmp@a{#1}%%
  \def\ae@tmp@b{#2}%%
  \s@ae@parse@line@aux}

\def\s@ae@parse@line@aux{%%
  \@ifnextchar[%]
  {\@s@ae@parse@line@aux}
  {\@s@ae@parse@line@aux[]}}

\def\@s@ae@parse@line@aux[#1]{%%
  \def\ae@tmp@c{#1}%%
  \edef\ae@tmp{[\expandonce\ae@tmp@c]{\expandonce\ae@tmp@a}{\expandonce\ae@tmp@b}}%%
  \expandafter\@ae@parse@line\ae@tmp}

作为egreg建议,我处理选修的通过定义一个论点辅助的宏。但正如指出的那样,如果空格出现在 之前,它仍然会干扰预期解析[。因此,我通过将前两个参数保存到宏来处理这个问题,然后我使用两个辅助宏。第一个测试是否有后续[(非常方便地为我吞噬空格)。然后这个第三个参数也被保存到宏中。然后我使用扩展技巧\@ifnextchar构建参数。\@ae@parse@line

相关内容