为什么 LaTeX 不实现单次传递引用?

为什么 LaTeX 不实现单次传递引用?

例子:

\documentclass{article}

\begin{document}


\section{Power series}\label{ps}

\begin{equation} \label{eq}
\sum_{i=0}^\infty a_i x^i.
\end{equation}

The equation \ref{eq} is a typical power series.

\section{Conclusion}
Look at Section~\ref{ps}.


\end{document}

为了获取引用,latex必须运行两次,并创建一个辅助文件。然而,请看以下类似的(不太冗长的)OpTeX 示例:

\sec[ps] Power series 

$$
\sum_{i=0}^\infty a_i x^i. \eqmark[eq]
$$

The equation \ref[eq] is a typical power series.

\sec Conclusion
Look at Section~\ref[ps].

\bye

我们只需运行optex一次即可获取引用。此外,无需.ref创建辅助 () 文件,因为在此示例中,引用已可在一次传递中解析。

因此,我不明白为什么 LaTeX 总是强制采用两次传递方法,即使一次传递也可以工作,并且可以处理最常见的参考类型(未来的参考较少见)。

答案1

“为什么”的问题并不容易回答,尤其是因为最初的系统是为具有当前机器所具有的内存的一小部分的机器设计的,但是......

确实,正如您所指出的,在某些情况下,可以一次性解决向后反向引用,但对于页面引用则不可能,对于前向引用也不可能。

首先值得注意的是,这在实践中没有任何区别,所以这只是一个理论问题:

  • 如果您正在编写文件,很少有人会在一个会话中编写整个文档,只运行一次 latex 并使用 pdf,因此解析交叉引用不需要额外运行 latex。它们会在需要解析时解析。

  • 如果您正在处理作为源提供的完整文档,那么通常它包含目录或图表列表或参考书目引用,因此即使\label更改为允许\ref在一次传递中向后传递,也需要多次传递才能解析所有引用。

从技术上讲,这会保存当前计数器和页面引用的有序数据对\label(或四倍)。通过将它们保存到文件中并在开始时读回,这两个值要么已知要么未知,并且可用于前向或后向引用。这简化了实现,尤其是简化了记录行为。hyperrefaux

请注意,optex 是在机器拥有更多可用内存的时代由不同的人设计的,因此在某些情况下它采取不同的设计决策也就不足为奇了,这无所谓对错。

事实上,latex 被记录为一个多通道系统,在各通道之间将数据存储到文件系统而不是内存中,这只是一种优化,让用户能够在每次编辑后只使用一次通道。您可以很容易地将其宣传为一个解析所有交叉引用的系统(例如 latexmk 或 context 所做的那样),方法是将其作为“内部实现细节”进行多次运行,并在将 PDF 返回给用户之前解析所有交叉引用。

答案2

你从一个错误的角度出发。

使用 OpTeX 你可以获取一个.ref写入的文件,以防一次运行不足以解决交叉引用,这可能发生在两种情况下:

  1. 未来的参考,或
  2. 在分页符附近设置了标签,并且看到标签时的页码与输出时的页码不同。

第一种情况很明显。对于第二种情况,考虑

Some text to artificially push the section too near the page break.

\vskip\dimexpr\vsize-4\baselineskip\relax

\sec[ps] Power series 

$$
\sum_{i=0}^\infty a_i x^i. \eqmark[eq]
$$

The equation \ref[eq] is a typical power series.

\sec Conclusion
Look at Section~\ref[ps] at page~\pgref[ps].

\bye

您将看到.ref将创建一个文件。日志将包含

WARNING l.18: Try to rerun to get references right.

由于分页异步机制,一次性解决交叉引用(甚至是过去的引用)的方法。如您所见,即使是过去的引用也可能需要两次传递。

如果您只是想要反向引用数字而不是页面,那么它即使使用超链接也应该可以工作,但这似乎是一个很大的限制。

相关内容