我正在尝试测试一个 if 条件,其中条件的名称取决于宏参数。为此,我使用\csname ifcondition#1 \endcsname
。这在简单的宏中运行良好,如下所示:
\newif\ifconditionA
\conditionAtrue
\def\test#1{
\csname ifcondition#1\endcsname
A: True
\fi
}
\test{A}
但是,在我的实际用例中,这个测试是分支的一部分\ifcase
,如下所示:
\documentclass{article}
\begin{document}
\newif\ifconditionA
\conditionAtrue
\def\test#1#2{
\ifcase#2
Case 0
\or
%\ifconditionA % This works
\csname ifcondition#1\endcsname
Case 1, A: true
\fi
\fi
}
\test{A}{0}
%\test{A}{1} % This works
\end{document}
此操作失败,并显示错误消息! Extra \fi. \test ...tion#1\endcsname Case 1, A: true \fi \fi
。
如果我直接使用条件的名称,不带\csname
,它可以正常工作,并且如果执行包含条件的分支,它也可以工作。
发生了什么事?我该如何解决这个问题?
答案1
限制是条件必须匹配,否则跳过未使用的分支将无法按预期工作。
方法有很多种。下面的例子使用\ifx
并将构造的条件与进行比较\iftrue
。因为我们已经有了\ifx
,所以后者也被掩盖了\csname
:
\documentclass{article}
\begin{document}
\newif\ifconditionA
\conditionAtrue
\def\test#1#2{%
\ifcase#2
Case 0
\or
\expandafter
\ifx\csname ifcondition#1\expandafter\endcsname
\csname iftrue\endcsname
Case 1, A: true
\fi
\fi
}
\test{A}{0}
\test{A}{1}
\end{document}
如果您希望在宏中使用一些更清晰的东西\test
,那么魔法可以隐藏在宏中,例如:
\documentclass{article}
\begin{document}
\newif\ifconditionA
\conditionAtrue
\newcommand*{\getcondition}[1]{%
T\expandafter
\ifx\csname ifcondition#1\endcsname\iftrue
\expandafter T%
\else
\expandafter F%
\fi
}
\def\test#1#2{%
\ifcase#2
Case 0%
\or
\if\getcondition{#1}%
Case 1, #1: true%
\else
Case 1, #1: false%
\fi
\else
Other case%
\fi
}
[\test{A}{0}]
[\test{A}{1}]
[\test{B}{0}]
[\test{B}{1}]
[\test{A}{2}]
\end{document}
答案2
你可以利用扩展标记的事实\if
,直到找到不可扩展的标记:
\documentclass{article}
\begin{document}
\newif\ifconditionA
\conditionAtrue
\def\testcondition#1{\expandafter\TTfi\csname ifcondition#1\endcsname}
\def\TTfi{TT\fi}
\def\test#1#2{%
\ifcase#2
Case 0
\or
\if\testcondition{#1}%
Case 1, A: true
\fi
\fi
}
\test{A}{0}
\test{A}{1}
\end{document}
让我们看看它是如何工作的。如果我们处于跳过的文本中,即条件的假分支或\or
要忽略的分支,TeX 将匹配\if
真正对应于的\fi
(和可能的) 。如果它处于真实分支中,则扩展为\else
\ifconditionA
\if\testcondition{A}
\if\expandafter\TTfi\csname ifconditionA\endcsname
\if\TTfi\ifconditionA
\if TT\fi\ifconditionA
\ifconditionA
因此与\if
第一个匹配\fi
,整个组\if TT\fi
消失,不做任何事。然后构造的与其和\ifconditionA
匹配。\else
\fi