我正在制作一个报告模板,需要以几种不同的方式呈现作者列表,其中一种方式是列出每个作者的表格,并为他们提供一个空间来签署文档的打印版本。
我有一个作者列表定义为
\newcommand{\reportAuthors}{Bob Jones,Sally Smith,Humpty Dumpty}
并尝试生成如下表格:
\begin{tabular}{|b{4cm}|b{6cm}|b{4cm}|}
\hline
\multicolumn{3}{l}{\begin{Large}\textbf{Signatures}\end{Large}} \\ \hline
Approved by: & & Bob Jones \\ \hline
Approved by: & & Sally Smith \\ \hline
Approved by: & & Humpty Dumpty \\ \hline
\end{tabular}
我尝试使用\@for
以下命令执行此操作:
\begin{tabular}{|b{4cm}|b{6cm}|b{4cm}|}
\hline
\multicolumn{3}{l}{\begin{Large}\textbf{Signatures}\end{Large}} \\
\hline
\makeatletter
\@for\authname:=\reportAuthors\do{%
Approved by: & & \authname \\
}
\makeatother
\end{tabular}
但这会产生一个错误,即\authname
未定义的控制序列。如果我删除,& &
这样就没有列了,错误就会消失,它会正确地迭代并插入每个名称……但当然,这让我没有按要求在正确的列中找到名称。
如果我把放在\authname
第一列(这不是模板应该有的,而只是为了测试一些东西),那么我得到的不是未定义的控制序列,而是“不完整\ifx
”。
那么,首先,\authname
如果我插入字符,是什么原因导致未定义的&
?其次,我该如何解决这个问题?
更新:我尝试结合一些发现的信息别处尝试按照马丁的建议尝试收集tabular
环境之外的行:
\newcommand{\tablecontent}{}
\makeatletter
\@for\signame:=\reportAuthors\do{%
\g@addto@macro\tablecontent{Approved by: & & \signame \\ \hline }%
}
\makeatother
\begin{tabular}{|b{4cm}|b{6cm}|b{4cm}|}
\hline
\multicolumn{3}{l}{\begin{Large}\textbf{Signatures}\end{Large}} \\
\hline
\tablecontent
\end{tabular}
这修复了错误,但导致第三列(应该\signame
是)单元格为空。我怀疑这是由于我对扩展缺乏了解,当它扩展时,定义\signame
超出了范围。\edef
到目前为止,摆弄它并没有真正起到作用,但也许有人可以指出一些缺陷……?
答案1
错误可能是由于&
在表格中处理的特殊方式(实际上是在内部使用\halign
)而导致的。\@for
循环可能在与不同的列(读取组)中执行\authname
。
如果您将行收集到第一个宏之外的宏中,则将节省空间。使用能够循环逗号分隔列表的包,tabular
这非常容易。您还可以使用它的列表生成宏。有关更多详细信息,请参阅其手册。etoolbox
\reportAuthors
\documentclass{article}
\newcommand{\reportAuthors}{Bob Jones,Sally Smith,Humpty Dumpty}
\usepackage{array}
\usepackage{etoolbox}
\begin{document}
\begingroup
\newcommand\tablecontent{}
\def\do#1{\appto\tablecontent{Approved by: & & #1 \\}}%
\expandafter\docsvlist\expandafter{\reportAuthors}
\begin{tabular}{|b{4cm}|b{6cm}|b{4cm}|}
\hline
\multicolumn{3}{l}{\begin{Large}\textbf{Signatures}\end{Large}} \\
\hline
\tablecontent
\end{tabular}
\endgroup
\end{document}
答案2
没有必要构造\tablecontent
第一个然后打印它。相反,你可以\docvslist
直接在环境内添加行tabular
:
\documentclass{article}
\usepackage{array}
\usepackage{etoolbox}
\usepackage{booktabs}
\newcommand\AuthorList[1]{%
\renewcommand*\do[1]{Approved by &&##1\\}
\begin{tabular}{|b{4cm}|b{6cm}|b{4cm}|}
\toprule
\multicolumn{3}{l}{\begin{Large}\textbf{Signatures}\end{Large}} \\
\midrule
\docsvlist{#1}
\bottomrule
\end{tabular}
}
\begin{document}
\AuthorList{Bob Jones,Sally Smith,Humpty Dumpty}
\end{document}
\reportAuthors
如果你想使用问题中的预定义列表,那么你需要
\expandafter\AuthorList\expandafter{\reportAuthors}
或用于\expandafter\docsvlist\expandafter{#1}
的定义\AuthorList
。