添加链接
link管理
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接
  • 处理超宽问题
  • 此篇将讨论 LaTeX 中的浮动算法。在此之后,读者应该有能力理解 LaTeX 中浮动体各种「乱跑」的现象的由来,并且知道关于 LaTeX 中浮动体一些最佳实践。

    浮动体相关的术语

    浮动体类型

    每个浮动体都从属于一种浮动体类型。默认情况下,LaTeX 定义了两种浮动体类型,即 figure table 。文档类和宏包的作者,可以在其中定义额外的浮动体类型(比如 listings 宏包定义了用于排版代码清单的浮动体; algorithm 宏包定义了用于排版算法的浮动体),用户也可以在导言区定义自己需要的浮动体类型(借助 float 宏包)。浮动体从属的类型,在多个方面会影响浮动体的最终位置。比如说,每个浮动体类型都有默认的位置选项,如果它们没有被浮动体本身的位置选项覆盖的话,那么就会生效。

    需要特别强调的是,同一个浮动体类型中的不同浮动体,它们的相对顺序是固定的。也就是说,不管浮动体如何「乱跑」,Figure 1, Figure 2, Figure 3 这样的顺序是始终保持的。(简称「你大爷始终是你大爷」原则)不过,不同类型的浮动体之间,其顺序则可能出现穿插。比如,如果有 Table 1,则可以出现在相对上述三个图片的任意位置。

    浮动区域

    在同一栏(column)当中,LaTeX 设置了两个浮动区域:栏的顶部和底部。对于双栏排版来说,LaTeX 还提供了额外的区域:跨过双栏的顶部。

    此外,LaTeX 种也有所谓的「浮动栏」或者「浮动页」的设定。顾名思义,浮动栏和浮动页就是「只有浮动体」的栏或者页。

    最后,LaTeX 也可以将浮动体放在文本内容的中间(当然,这需要显式指定)。

    浮动体位置选项

    为了指定浮动体放置的位置,手稿作者需要给浮动体环境传入浮动体位置选项(通过环境的可选参数)。如果手稿作者没有显式提供位置选项,那么 LaTeX 则会使用浮动体所述类型所指定的位置选项。

    1
    2
    3
    \begin{figure}[!htbp]
    % ...
    \end{figure}

    LaTeX 中默认的浮动体位置选项有五种,手稿作者可以 以任意顺序 组合使用这些选项。它们是

  • ! 表示忽略一些严格的限制条件(后文详述);
  • h 表示如有可能,则放在当前位置;
  • t 表示该浮动体允许置于栏的顶部;
  • b 表示该浮动体允许置于栏的底部;
  • p 表示该浮动体允许置于浮动栏或浮动页。
  • 这也就是说,如果某个字符(比如 b )没有出现在浮动体位置选项中,则 LaTeX 在尝试输出该浮动体时,就不会试着将它放在栏的底部。

    需要再次强调的是,浮动体位置选项的指定是一个「组合」问题,而不是「排列问题」。因此, [tb] [bt] 是等效的。并不是说 [bt] 表示首先尝试放在栏的底部。

    浮动算法参数

    总计,大约有 20 个参数,会最终影响到 LaTeX 的浮动体算法。根本来说,这些参数限制了

  • 某个浮动区域至多允许摆放多少个浮动体,
  • 浮动区域的大小,
  • 非浮动栏或非浮动页中,文字区域的最小大小,
  • 一个浮动区域内连续浮动体之间的垂直距离,以及
  • 浮动区域与其前后文字区域的垂直距离。
  • 浮动体参考点

    显而易见,浮动体在手稿源代码中的位置,会影响最终的输出位置。因为,浮动体在手稿源代码中的位置,决定了 LaTeX 在何时第一次遇见这个浮动体。如果,浮动体在手稿的源代码中,被置于一个段落的中间,那么这个浮动体的参考点是(自源代码中观察)浮动体之后的(自最终输出文件观察)下一个断行点或者分页点。

    浮动算法

    至此,我们可以开始探讨 LaTeX 浮动算法的行为了。

    在理解浮动算法之前,我们有必要强调一下,这个算法是在 1980 年代设计出来的。其时,计算机的算力相对现在是非常有限的。因此,浮动算法的设计中有非常多的「妥协」。

    基于这一原因,LaTeX 中所有的排版算法,都在尽力避免「回溯」。这也就是说,LaTeX 读入源代码之后,会试着尽可能快地将之排版出来。这样一来,算法的复杂度就可以尽量的低——当然,它依然很复杂,并因此可以尽快输出排版结果。

    对于浮动体来说,这就意味着确定浮动体位置的浮动算法必须是一个 贪心算法 。在 LaTeX 遇见浮动体时,它就会尽可能地尝试输出它。如果 LaTeX 确定输出了一个浮动体,那么不论之后遇到什么内容,它的位置都不会发生改变。这种贪心实际上是对运行效率的妥协。因为,显而易见地,如此贪心的位置选择,可能在读入之后的数据以后,可以发现是不那么完美的。

    比如说,假设一个图片允许放在栏的顶部或者底部。而后 LaTeX 可能会将其放在某一栏的顶部区域。现在假设,在这个图片之后,假设有两个表格, 允许放在栏的顶部,那么这两个表格就没地方可防了——必须放在下一页。而实际上,最好的选择是,将这两个表格放在顶部,而图片放在底部。(在这个假设中,最佳的放置办法,LaTeX 是不会去尝试的)

    基本流程

    浮动算法的基本流程,可以大致描述如下。

  • 当 LaTeX 遇到一个浮动体,它会根据浮动算法的规则(后文详述)尽可能快地输出该浮动体。
  •