# Pgffor and the alignment character (&)

I need to construct a table that looks like:

\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}


for any given number of colums or rows. In fact I only need the part that has arrow next to it, because I would like to be able to put it in different kinds of environments.

I need it to come like some sort of macro, so I can do

\begin{tabular}{ccc}
\generate{a}{3}{3}
\end{tabular}


to get the above table. I've tried:

\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}


Yet I get this error:

Incomplete \ifnum; All text was ignored after line 81.
Missing \endgoup inserted.
....


## What I need

I need a macro to quickly build tabular environments that have a variable number of colums and rows, yet I want to be able to use the tabular as I would do every day:

\begin{tabular}{cc|cc}
\hline
\hline
foo & bar & baz \\
\makematrix{a}{4}{3}    % <-- makes the rest of the table as described below
\hline
bar & baz &baz\\
\end{tabular}


etc. So The macro must be just inputted into the tabular environment, and behave as if

a(1,1) & a(1,2) & a(1,3)\\
a(2,1) & a(2,2) & a(2,3)\\
...


were inputted at that spot. Similarly, I would like to be able to define the colums of the tabular environment myself because I'd like to be able tu use > {...} on the columns.

-
You can try independently to use pgffor package and nest two foreach loops to run over all rows and columns. –  percusse Jan 6 '12 at 12:34
yes but I can't get the &'s to be inserted without pgf giving an error –  romeovs Jan 6 '12 at 12:40
TeX conditionals cannot start in a table cell and end in another one. –  egreg Jan 6 '12 at 14:01
@egreg so it cannot be done? –  romeovs Jan 6 '12 at 14:22
@romeovs Yes, in many ways. –  egreg Jan 6 '12 at 14:30
show 1 more comment

This is a possible implementation.

\documentclass{article}

\newtoks\romeotoks
\makeatletter
\newcommand{\makematrix}[4][]{%
{\global\romeotoks={}%
\@tempcnta=\z@ \@tempcntb=\z@
\loop\ifnum\@tempcnta<#3
{\loop\ifnum\@tempcntb<#4
\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
\hline
foo & bar & baz \\
\makematrix{a}{4}{3}
\hline
bar & baz &baz\\
\hline
\end{tabular}

\end{document}


The optional argument to \makematrix is something to be put at the end of each row, for example

\makematrix[\hline]{a}{4}{3}


\makematrix has a first optional argument that contains what you want to put after the \\ on each row (for instance, \hline).

## EDIT

Here's a LaTeX3 version:

\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


The usage is exactly the same. However I've split the business into two parts, so one can say also

\preparematrix{a}{4}{3}
\begin{tabular}{cc|c}
\hline
\hline
foo & bar & baz \\
\usematrix
\hline
bar & baz &baz\\
\hline
\end{tabular}


in case one has to make special adjustments in the first column with \collectcell.

-
@romeovs The problem is exactly that you can't (easily) do that inside a tabular. Try and show a real example of what you need. –  egreg Jan 6 '12 at 15:38
@romeovs See edited answer –  egreg Jan 6 '12 at 16:43
@romeovs I've added a LaTeX3 version and tried a simple collcell setting, it worked. But also the old version did. –  egreg Feb 10 '12 at 22:51
@romeovs With this implementation the entire submatrix is built when LaTeX is already in the first cell of a row, so it cannot work when the first column is given special treatment with \collectcell. –  egreg Feb 11 '12 at 9:29
@romeovs I added the version that can prepare the matrix outside the tabular and then use it inside. –  egreg Feb 11 '12 at 13:46