我需要构建一个如下所示的表格:
\begin{tabular}{ccc}
a(1,1) & a(1,2) & a(1,3)\\ % <---
a(2,1) & a(2,2) & a(2,3)\\ % <--- I need this
a(3,1) & a(3,2) & a(3,3)\\ % <---
\end{tabular}
对于任何给定的列数或行数。实际上,我只需要旁边有箭头的部分,因为我希望能够将其放在不同类型的环境中。
我需要它像某种宏一样出现,这样我就可以做到
\begin{tabular}{ccc}
\generate{a}{3}{3}
\end{tabular}
获取上表。我尝试过:
\newcommand\makerow[3]{
\foreach \n [count=\ni] in {1,...,#3}{%
\ifnum\ni=1
#1(#2,\n)
\else
& #1(#2,\n)
\fi
}%
}%
\newcommand\makematrix[3]{
\foreach \m [count=\mi] in {1,...,#2}{%
\ifnum\mi=#2
\makerow{#1}{\m}{#3}
\else
\makerow{#1}{\m}{#3}\\
\fi
}%
}%
\begin{tabular}{ccc}
\makematrix{a}{3}{3}
\end{tabular}
但我收到了这个错误:
Incomplete \ifnum; All text was ignored after line 81.
Missing \endgoup inserted.
....
我需要的
我需要一个宏来快速构建具有可变数量的列和行的表格环境,但我希望能够像每天一样使用表格:
\begin{tabular}{cc|cc}
\hline
header 1 & header 2 & header 3\\
\hline
foo & bar & baz \\
\makematrix{a}{4}{3} % <-- makes the rest of the table as described below
\hline
bar & baz &baz\\
\end{tabular}
等等。因此,宏必须输入到表格环境中,并且表现得好像
a(1,1) & a(1,2) & a(1,3)\\
a(2,1) & a(2,2) & a(2,3)\\
...
在该位置输入。同样,我希望能够tabular
自己定义环境的列,因为我希望能够> {...}
在列上使用。
答案1
这是一种可能的实现方式。
\documentclass{article}
\newtoks\romeotoks
\makeatletter
\newcommand{\makematrix}[4][]{%
{\global\romeotoks={}%
\@tempcnta=\z@ \@tempcntb=\z@
\loop\ifnum\@tempcnta<#3
\advance\@tempcnta\@ne
{\loop\ifnum\@tempcntb<#4
\advance\@tempcntb\@ne
\edef\next{%
\ifnum\@tempcntb=\@ne\else&\fi
\unexpanded{#2}(\number\@tempcnta,\number\@tempcntb)}%
\global\romeotoks=\expandafter{\the\expandafter\romeotoks\next}%
\repeat}%
\@tempcntb=\z@
\global\romeotoks=\expandafter{\the\romeotoks \\ #1}%
\repeat}%
\the\romeotoks}
\makeatother
\begin{document}
\begin{tabular}{cc|c}
\hline
header 1 & header 2 & header 3\\
\hline
foo & bar & baz \\
\makematrix{a}{4}{3}
\hline
bar & baz &baz\\
\hline
\end{tabular}
\end{document}
可选参数\makematrix
是放在每行末尾的内容,例如
\makematrix[\hline]{a}{4}{3}
\makematrix
有第一个可选参数,其中包含您想要\\
在每行后面放置的内容(例如\hline
)。
编辑
这是 LaTeX3 版本:
\usepackage{xparse}
\ExplSyntaxOn
\tl_new:N \l_romeo_cells_tl
\int_new:N \l_romeo_row_int
\int_new:N \l_romeo_col_int
\NewDocumentCommand { \preparematrix } { O{} m m m }
{
\tl_set:Nn \l_romeo_cells_tl { }
\int_set:Nn \l_romeo_row_int { #3 }
\int_set:Nn \l_romeo_col_int { #4 }
\prg_stepwise_inline:nnnn { 1 } { 1 } { \l_romeo_row_int }
{
\prg_stepwise_inline:nnnn { 1 } { 1 } { \l_romeo_col_int }
{
\int_compare:nF { ####1 = 1 } { \tl_put_right:Nn \l_romeo_cells_tl { & } }
\tl_put_right:Nn \l_romeo_cells_tl
{ #2 ( ##1 , ####1 ) }
}
\tl_put_right:Nn \l_romeo_cells_tl { \\ #1 }
}
}
\DeclareExpandableDocumentCommand{ \usematrix } { }
{ \tl_use:N \l_romeo_cells_tl }
\NewDocumentCommand{ \makematrix } { O{} m m m }
{ \preparematrix[#1]{#2}{#3}{#4}\usematrix }
\ExplSyntaxOff
用法完全相同。不过,我将业务分为两部分,因此也可以说
\preparematrix{a}{4}{3}
\begin{tabular}{cc|c}
\hline
header 1 & header 2 & header 3\\
\hline
foo & bar & baz \\
\usematrix
\hline
bar & baz &baz\\
\hline
\end{tabular}
以防必须在第一列中做出特殊调整\collectcell
。