第一章出现在目录第一行之前

第一章出现在目录第一行之前

我的书中有一个目录memoir。我希望每章都有一行,此外还有每组类似章节的标题。

由于某种原因,第一章的行出现在第一phantom行之前。

\documentclass{memoir}

\begin{document}

\frontmatter
\tableofcontents*

\mainmatter

\phantomsection
\addcontentsline{toc}{part}{Topic 1}

\include{intro}

\chapter{Chapter 2}

This is the second chapter.

\phantomsection
\addcontentsline{toc}{part}{Topic 2}

\chapter{Chapter 3}

This is the third chapter.

\chapter{Chapter 4}

This is the fourth chapter.

\end{document}

intro.tex同一目录中的文件包含以下内容:

\chapter{Introduction} \label{chap:intro}

\noindent This is the introductory chapter.

我注意到,如果我将 的内容粘贴intro.tex到主文件中(而不是使用\include),问题就解决了——目录中的“简介”行出现在“主题 1”之前!然而,这不是一个好的解决方案,因为我有大型章节文件,我想单独包含它们……

什么原因可能导致此问题?有办法解决吗?

答案1

\addcontentsline这是(或\addtocontents)和 的一个众所周知的问题\include;只需移动这些线

\phantomsection
\addcontentsline{toc}{part}{Topic 1}

到文件intro.tex

让我们看一下问题的原因;为简单起见,我们考虑以下示例文件main.tex

\documentclass{memoir}

\begin{document}

\tableofcontents*

\mainmatter

\addcontentsline{toc}{part}{Topic 1}
\include{intro}
\chapter{Chapter 2}

\end{document}

文件 intro.tex 类似于

\chapter{Introduction}

Text

当然,在真实的文档中“第 2 章”也应该写在它自己的.tex文件中并\includ编辑main.tex,但这与下面的解释无关。

这里有两件事很重要:

  1. 每个\included 文件都会生成其自己的.aux文件。
  2. 有关目录的信息不会直接写入.toc文件;\@write程序首先进入.aux文件,并且仅在执行时才\enddocument从文件读取该信息.aux并将其写入文件.toc

现在,让我们来看一下 的处理步骤main.tex。在\end{document}到达 之前,文件main.auxmain.toc仍为空,但至关重要的是, 该文件intro.aux已被写入,并且包含(除其他内容外) 行。

\@writefile{toc}{\contentsline {chapter}{\chapternumberline {1}Introduction}{1}}

\enddocument执行时,文件main.aux将被处理并包含以下行

\@writefile{toc}{\contentsline {part}{Topic 1}{1}}
\@writefile{lof}{\addvspace {10pt}}
\@writefile{lot}{\addvspace {10pt}}
\@writefile{toc}{\contentsline {chapter}{\chapternumberline {2}Chapter 2}{3}}

此外,写入.toc文件的操作已完成,但完成时,顺序并非预期(请记住,是intro.aux先写入的):与“简介”相关的写入将首先完成,然后是“主题 1”的写入,最后是“章节 2”的写入。事实上,文件main.toc

\contentsline {chapter}{\chapternumberline {1}Introduction}{1}
\contentsline {part}{Topic 1}{1}
\contentsline {chapter}{\chapternumberline {2}Chapter 2}{3}

文档的下一步处理将会按该顺序查找行,并且这些行将以错误的顺序排版在文档中。

可能的解决方案

  1. 将该\addtocontents行移至 的开头intro.tex。这样做后,intro.aux写入时将包含以下行

    \@writefile{toc}{\contentsline {part}{Topic 1}{1}}
    \@writefile{lof}{\addvspace {10pt}}
    \@writefile{lot}{\addvspace {10pt}}
    \@writefile{toc}{\contentsline {chapter}{\chapternumberline {1}Introduction}{1}}
    

    所以现在文件\@write中的 s.toc将按正确的顺序排列:

    \contentsline {part}{Topic 1}{1}
    \contentsline {chapter}{\chapternumberline {1}Introduction}{1}
    \contentsline {chapter}{\chapternumberline {2}Chapter 2}{3}
    

    我知道这可能听起来很“黑客”,但其他替代解决方案(见下文)也或多或少具有相同的性质。

  2. 如果您不需要\includeonly的功能\include,您可以改用\input(但请注意,\input不会在内部发出\cleardoublepage\clearpage)。\input不会.aux为附属文件生成文件,这将避免出现问题。

  3. 如果您需要使用\include,并且所有包含的文件将在必要时负责发出\cleardoublepage\clearpage(例如,如果所有包含的文件都包含\chapter),那么您可以按原样处理文档;这将在目录中产生错误的顺序),但会让您从功能中获利\includeonly,然后,对于最终版本,将所有\include命令替换为\input命令并执行最终的完整处理(根据文档的要求执行尽可能多的运行)。

  4. 为该行使用子文件,\addtocontents并将\include其放在主文档中。在示例中,main.tex现在看起来如下所示:

    \mainmatter
    
    \include{topic1}
    \include{intro}
    \chapter{Chapter 2}
    

    包含topic1.tex

    \addcontentsline{toc}{part}{Topic 1}
    

相关内容