Quero gerar uma tabela com o \foreach
comando de forma que as entradas da tabela dependam da linha e da coluna. Eu queria testar o seguinte código:
\documentclass{article}
\usepackage{pgffor,etoolbox}
\newcommand*\tas[2]{
\pgfmathsetmacro{\sat}{#1+#2}
\sat
}
\newcommand*\mytablecontents{}
\foreach \i in {1,...,7}{
\foreach \j in {1,...,7}{
\xappto\mytablecontents{\tas{\i}{\j}}
\gappto\mytablecontents{&}
}
\gappto\mytablecontents{\\}
}
\begin{document}
\begin{tabular}{c|cc|ccc|cc}
\mytablecontents
\end{tabular}
\end{document}
Isso dá o erro "Incomplete\iffalse". Eu li que o motivo desse erro é o uso do \pgfmathsetmacro
. Alguém sabe como lidar com isso?
Responder1
\pgfmathsetmacro
não é expansível, portanto não é “avaliado” em an \edef
(que é o que \xappto
faz, na variante \xdef
).
Você pode primeiro calcular a soma, armazenando-a em uma macro e depois anexar a versão expandida:
\documentclass{article}
\usepackage{pgffor,etoolbox}
\newcommand*\tas[2]{%
\pgfmathsetmacro{\sat}{#1+#2}%
}
\newcommand*\mytablecontents{}
\foreach \i in {1,...,7}{%
\foreach \j in {1,...,7}{%
\tas{\i}{\j}%
\xappto\mytablecontents{\sat &}
}%
\gappto\mytablecontents{\\}
}
\begin{document}
\begin{tabular}{c|cc|ccc|cc}
\mytablecontents
\end{tabular}
\end{document}
Alternativamente, você pode usar aritmética expansível: expl3
fornece, com xfp
e \fpeval
:
\documentclass{article}
\usepackage{pgffor,etoolbox,xfp}
\newcommand*\mytablecontents{}
\foreach \i in {1,...,7}{%
\foreach \j in {1,...,7}{%
\xappto\mytablecontents{\fpeval{\i+\j}&}
}%
\gappto\mytablecontents{\\}
}
\begin{document}
\begin{tabular}{c|cc|ccc|cc}
\mytablecontents
\end{tabular}
\end{document}
Apenas para mostrar os recursos (nem todos cobertos por pgfmath
estão disponíveis), se você alterar a \xappto
chamada para
\xappto\mytablecontents{\fpeval{round(\i*sqrt(\j),2)}&}
a saída seria
O mesmo resultado com expl3
código completo:
\documentclass{article}
\usepackage{expl3}
\ExplSyntaxOn
\tl_clear:N \l_tmpa_tl
\int_step_inline:nnnn { 1 } { 1 } { 7 }
{ % outer cycle: #1
\int_step_inline:nnnn { 1 } { 1 } { 7 }
{ % inner cycle: ##1
\tl_put_right:Nx \l_tmpa_tl { \fp_eval:n {round(#1*sqrt(##1),2)} & }
}
\tl_put_right:Nn \l_tmpa_tl { \\ }
}
\tl_set_eq:NN \mytablecontents \l_tmpa_tl
\ExplSyntaxOff
\begin{document}
\begin{tabular}{c|cc|ccc|cc}
\mytablecontents
\end{tabular}
\end{document}
Observe que \tl_put_right:Nx
é o análogo de \eappto
( x
significa expanded) e \tl_put_right:Nn
é o análogo de \appto
. Não há necessidade de definições globais, pois \int_step_inline:nnnn
não utiliza agrupamento de ciclos: o índice atual está disponível diretamente como #1
(ou ##1
no loop interno).
Responder2
Para evitar usar isso newcommand
, você pode calcular o mesmo resultado usando a opção [evaluate = \j as \c using int(\i+\j)]
do \foreach
loop interno.
\documentclass{article}
\usepackage{pgffor,etoolbox}
\newcommand*\mytablecontents{}
\foreach \i in {0,...,7}{
\foreach \j [evaluate = \j as \c using int(\i+\j)] in {0,...,7}{
\xappto\mytablecontents{\c}
\gappto\mytablecontents{&}
}
\gappto\mytablecontents{\\}
}
\begin{document}
\begin{tabular}{c|cc|ccc|cc}
\mytablecontents
\end{tabular}
\end{document}
Você também pode usar:
\newcommand*\mytablecontents{}
\foreach \i in {0,...,7}{
\foreach \j in {0,...,7}{
\pgfmathtruncatemacro\c{\i+\j}
\xappto\mytablecontents{\c}
\gappto\mytablecontents{&}
}
\gappto\mytablecontents{\\}%
}
Responder3
Sua execução de
\xappto\mytablecontents{\tas{\i}{\j}}
assume que \tas{.}{.}
é expansível. No entanto, como contém uma atribuição ( \pgfmathsetmacro
), não é. Portanto, você terá que avaliar (expandir) a expressão primeiro antes de incluí-la como parte do seu app
endage para \mytablecontents
. Como a expressão é bastante direta (a adição de dois números), você pode simplesmente usar \number\numexpr#1+#2
:
\documentclass{article}
\usepackage{pgffor,etoolbox}
\newcommand*\tas[2]{%
\number\numexpr#1+#2\relax
}
\newcommand*\mytablecontents{}
\foreach \i in {1,...,7}{
\foreach \j in {1,...,7}{
\xappto\mytablecontents{\tas{\i}{\j}}
\gappto\mytablecontents{&}
}
\gappto\mytablecontents{\\}
}
\begin{document}
\begin{tabular}{c|cc|ccc|cc}
\mytablecontents
\end{tabular}
\end{document}
O cálculo expansível é facilmente possível através da interface LaTeX2e para \fp_eval
LaTeX3 noxfp
pacote:
\usepackage{pgffor,xfp,etoolbox}
\newcommand*\mytablecontents{}
\foreach \i in {1,...,7}{
\foreach \j in {1,...,7}{
\xappto\mytablecontents{\fpeval{\i+\j}}
\gappto\mytablecontents{&}
}
\gappto\mytablecontents{\\}
}