2

I have seperate .tex files in a directory named chapters in the main directory. I would like to include/input those. After some research a solution like the one below could be possible. Unfortunately I get "Undefined control sequence."

   \ForEach \i in {1,...,10}{
    \InputIfFileExists{chapters/\i.tex}
   }
4
  • 2
    \ForEach should be \foreach.
    – user11232
    Feb 8, 2015 at 12:50
  • This appears to be the same question asked by a different user yesterday tex.stackexchange.com/questions/226897/… Feb 8, 2015 at 13:22
  • 2
    In order to use \foreach (not \ForEach), you have to add \usepackage{pgffor}.
    – egreg
    Feb 8, 2015 at 13:38
  • The syntax is \InputIfFileExists{filename}{true branch}{false branch}, as far as I know (amongst \foreach) of course
    – user31729
    Feb 8, 2015 at 14:47

2 Answers 2

5

Some remarks:

  • \ForEach might be defined by some package, but the syntax looks like pgf's \foreach. TeX/LaTeX is case sensitive. At least package pgffor should then be loaded unless TikZ or pgf is used anyway.

  • \i is a quite bad name for including text files, because \i might be used in some languages, it usually generates a "i" without dot: ı. The example therefore uses \ChapterNumber.

  • \InputIfFileExists takes three arguments, the file name and two code arguments for the cases that the file exists and is missing.

  • It seems, that chapter files are included, which should start and end at page boundaries. Then \include is the better choice. It internally uses \InputIfFileExists. Thus the compilation continues without error, if the chapter is not yet written. Then a reminder is printed on the console/log file, e.g.:

    No file chapters/7.tex.
    

    If the files are input via \include, then it is easy to compile only one chapter using \includeonly.

A full example can look like:

\documentclass{book}
\usepackage{pgffor}
\begin{document}
\foreach \ChapterNumber in {1, ..., 10} {
  \include{chapters/\ChapterNumber}
}
\end{document}

Macro \foreach puts the loop body into a group. This can be advantage, if local definitions should not leak out the chapters. Or a disadvantage, e.g. if the introduction chapter defines something that is supposed to be used in other chapters as well.

A loop without group and without additional packages:

\documentclass{book}
\begin{document}   

\makeatletter
\newcounter{FileNumber}
\@whilenum\value{FileNumber}<10 \do{%
  \stepcounter{FileNumber}
  \makeatother
  \include{chapters/\number\value{FileNumber}}%
}
\makeatother  

\end{document}

But I think, the structure of the document is much easier to understand, if the chapter file names contains real names instead of numbers:

\include{chapters/Introduction}
\include{chapters/History}
\include{chapters/Theory}
\include{chapters/Setup}
\include{chapters/Experiments}
\include{chapters/Results}
\include{chapters/Summary}

As compromise numbers can be added to show the correct chapter sorting order in a directory listing:

\include{chapters/01-Introduction}
...
\include{chapters/10-Summary}
4
  • Doing \include inside a group doesn't seem like a very good idea.
    – egreg
    Feb 10, 2015 at 11:48
  • @egreg I have extended the answer. More elaborate solutions have the danger, that the simple task of including 10 files looks like a large program than a document. Writing, reading, maintaining, understanding such a program requires much, much more time than a simple plain list of \include statements (preferable with more speaking names). Feb 10, 2015 at 12:22
  • An automized version (not with \include) could be invaluable if there's a long list of files to input (tables, for instance).
    – egreg
    Feb 10, 2015 at 12:25
  • +1 for the named chapter files. chapter01.tex tells me nothing, and becomes meaningless if chapters are re-ordered.
    – jja
    Feb 10, 2015 at 12:38
3

You should use \foreach after doing

\usepackage{pgffor}

(or \usepackage{tikz}). However there's a problem with \foreach: each cycle is performed in a group, so you'd be including the files in a group, which might have undesired consequences.

Also \i would be interpreted incorrectly if used in one of the files.

Solution:

\newtoks\listoffilestoinput
\foreach \i in {1,...,10}{%
   \edef\temp{%
     \the\listoffiles
     \noexpand\InputIfFileExists{chapters/\i.tex}{}{}%
   }%
   \global\listoffilestoinput=\expandafter{\temp}
}
\the\listoffilestoinput

Don't forget the trailing arguments to \InputIfFileExists

Of course you can use \include instead of \InputIfFileExists, if you so prefer:

\newtoks\listoffiles
\foreach \i in {1,...,10}{%
   \edef\temp{%
     \the\listoffilestoinput
     \noexpand\include{chapters/\i}%
   }%
   \global\listoffilestoinput=\expandafter{\temp}
}
\the\listoffilestoinput

Note that the extension should not be added with \include (it is optional with \InputIfFileExists, where .tex is implicit if no extension is present).

You might even abstract this in a macro to be defined in the preamble.

\newtoks\listoffilestoinput
\newcommand{\multiinclude}[3][\i]{%
   \global\listoffilestoinput={}% reinitialize
   \foreach #1 in {#2}{%
     \edef\temp{%
       \the\listoffilestoinput
       \noexpand\include{#3}%
       %\noexpand\InputIfFileExists{#3}{}{}% alternative version
     }%
   \the\listoffilestoinput
}

Then in the document you can use

\multiinclude{1,...,10}{chapters/\i}

or also

\multiinclude[\ChapterNumber]{1,...,10}{{chapters/\ChapterNumber}

The first mandatory argument is the list for \foreach, the second mandatory argument is the template. The optional argument (default \i) is the variable to use.

Note that with this approach (independently of the form you use), the variable \i is used just temporarily and has no side effects even if it is already defined (provided you don't use \foreach or \include as the variable name, of course); \i is perfectly good for this purpose.

0

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .