我正在学习\foreach
看看它是否能完成我想要做的事情。我不明白为什么下面的代码没有产生预期的输出。
平均能量损失
\documentclass[12pt,titlepage]{article}
\usepackage{pgffor}
\setlength\parindent{0pt}
\def\mydata{
{1,2},
{3,4}
}
\begin{document}
\foreach \x in \mydata
{
now starting new entry....\\
\foreach \y in \x
{
\y \\
}
}
\end{document}
以上生成
我希望第二个列表{3,4}
也显示在单独的行上。
我究竟做错了什么?
2014 年
更新
我发现问题在于最后一个条目必须与结束符位于同一行}
,就像这样
\def\mydata{
{1,2},
{3,4},
{5,6}}
如果上面写成
\def\mydata{
{1,2},
{3,4},
{5,6}
}
然后就会出现同样的问题。
答案1
有一些调试输出:
\documentclass[12pt,titlepage]{article}
\usepackage{pgffor}
\setlength\parindent{0pt}
\def\mydata{
{1,2},
{3,4}
}
\begin{document}
\foreach \x in \mydata
{
now starting new entry [\texttt{\detokenize\expandafter{\x}}]\\
\foreach \y in \x
{
\y \\
}
}
\end{document}
可以看出,逗号分隔列表的解析并不完美,一些空格被删除,即条目开头的空格,但条目结尾的空格仍然存在。在第二种情况下,由于尾随空格,值没有外括号,而内括号\foreach
将看到一个值而不是列表。
可以通过注释行尾来修复此问题。
\documentclass[12pt,titlepage]{article}
\usepackage{pgffor}
\setlength\parindent{0pt}
\def\mydata{
{1,2},
{3,4}%
}
\begin{document}
\foreach \x in \mydata
{
now starting new entry [\texttt{\detokenize\expandafter{\x}}]\\
\foreach \y in \x
{
\y \\
}
}
\end{document}
顺便说一句,最新的版本\\
将导致“Underfull \hbox
”警告。例如,可以通过以下方法修复此问题:
\documentclass[12pt,titlepage]{article}
\usepackage{pgffor}
\setlength\parindent{0pt}
\def\mydata{
{1,2},
{3,4}%
}
\newif\ifprevious
\begin{document}
\global\previousfalse
\foreach \x in \mydata
{
\ifprevious\\\fi
\global\previoustrue
now starting new entry [\texttt{\detokenize\expandafter{\x}}]%
\foreach \y in \x
{
\\\y
}
}
\end{document}
评论:全局赋值是必要的,因为\foreach
将循环体放入一个组中。
答案2
您有虚假的空间
\documentclass[12pt,titlepage]{article}
\usepackage{pgffor}
\setlength\parindent{0pt}
\def\mydata{{1,2},{3,4}}
\begin{document}
\foreach \x in \mydata
{
now starting new entry....\\
\foreach \y in \x
{
\y \\
}
}
\end{document}
答案3
这不是一个直接的答案,但我只想提一下,还有其他解决方案,例如xintFor
来自xinttools
图书馆。
\documentclass[preview, border=7mm]{standalone}
\usepackage{xinttools}
% spaces before and after commas are deleted
\def\mydata{
{1,2},
{3,4}
}
\begin{document}
\xintFor #1 in {\mydata} \do {
now starting new entry....\\
\xintFor #2 in {#1} \do {
#2 \\
}
}
\end{document}