我想知道哪些是本质区别makeindex
和xindy
(或)之间texindy
,其含义如下:
- 哪些事情我们能做而
xindy
哪些不能做makeindex
?反之亦然。 - 它们每个的主要用途是什么?
- 它们之间的句法差异样式文件. (
.ist
對比.xdy
)
答案1
简短答案
xindy
比 灵活得多makeindex
。与 不同makeindex
,xindy
支持 UTF8,可以根据不同的语言规则进行排序,并且可以支持欧洲和罗马数字系统之外的枚举系统。 UTF8 支持与 配合使用效果最佳,xindy -I xindy
而不是与texindy
( xindy -I latex
) 配合使用。
长答案
哪些事情我们可以做而哪些事情
xindy
我们不能做makeindex
?
这xindy 常见问题解答xindy
提供了有用的摘要,说明了可以做但 不能做的事情makeindex
。以下是该摘要的节选版:
国际化
xindy
可以配置为处理具有不同字母集和不同排序规则的多种语言的索引。[makeindex
针对英文字母进行硬编码。]位置类
makeindex
能够识别和处理阿拉伯数字、罗马数字和字母表作为索引位置的说明符。这些的简单复合结构也可以处理。xindy
提供了一个强大的声明方案,称为 位置类别。[这意味着您可以采用完全不同的编号方案来表示位置(例如,象形文字数字)。]属性的概念
可以
makeindex
使用封装器为每个索引条目分配一个标记(通常在索引条目命令中位于竖线符号后面)。例如在规范中\index{xindy|bold}
封装器是粗体,它在标记阶段封装页码。必须提供额外的 TeX 宏才能为某些标记分配页码。这个概念已被完全放弃,取而代之的
xindy
是更强大的方案,即属性。属性可用于 (i) 定义几个具有位置的分组和排序规则,我们可以定义 (ii) 文档准备系统的标记标签。交叉引用
交叉引用是在 中
makeindex
通过封装机制实现的,该机制仅用于标记目的。在 中已将其完全分离xindy
。
除了上述情况之外,还有一件事您可以做xindy
但不能做,makeindex
那就是拥有任意子级别。makeindex
您只能使用主级别(级别 0)、第一个子级别和第二个子级别条目。
或相反亦然。
我能想到的唯一优点makeindex
是:xindy
makeindex
应与所有 TeX 安装一起安装。没有安装的 TeX 安装makeindex
很可能非常旧。但是,xindy
仅包含在 TeX Live 中,因此 MikTeX 用户需要单独安装它。xindy
是 Perl 脚本,因此您必须在计算机上安装 Perl 解释器。这对某些 Windows 用户来说是一个障碍。类 Unix 系统往往预装了 Perl。makeindex
通常与受限模式配合使用\write18
,但上次我尝试使用xindy
受限模式调用\write18
时,它被禁用了。我预计它最终会被添加到允许的应用程序列表中。(我看不出有什么理由不允许它。)
它们每个的主要用途是什么?
排序和整理。两者都读取包含一组术语及其相关位置(或交叉引用)的文件。这些术语根据指定的字母表(英文字母表makeindex
,或所选的字母表)进行排序。xindy
)进行排序。术语可能具有应该用于实际排序比较的对应键。然后,将每个术语的多次出现合并为具有排序的单个条目位置列表。位置列表中的连续编号可以压缩为一个数字范围。然后将此信息写入另一个文件,该文件可以由应用程序(例如tex
或 )输入latex
。(输出标记可以通过样式文件或模块更改,这意味着虽然makeindex
和xindy
经常与 TeX/LaTeX 一起使用,但它们也可以与其他系统一起使用。)
它们的样式文件之间的语法差异。(
.ist
vs.xdy
)
该格式的语法.ist
比该格式简单得多.xdy
,但这是因为它具有更强的限制性。
makeindex
样式格式 ( .ist
)
这只是一份清单⟨说明符⟩ ⟨属性⟩对。说明符分为两组:输入说明符和输出说明符。
输入说明makeindex
符指示输入的格式。请考虑以下文档:
\documentclass{article}
\usepackage{makeidx}
\makeindex
\begin{document}
Duck\index{duck|textbf}.
Zebra\index{zebra}\index{stripy|see{zebra}}
\newpage
Aardvark\index{aardvark}
Zebra\index{zebra}
\emph{The Rise and Fall of the Duck Empire}%
\index{Rise and Fall of Duck Empire@\emph{The Rise and Fall of the Duck Empire}}%
\newpage
Zebra\index{zebra}
Duck\index{duck}
Aardvark\index{aardvark}
Mallard\index{duck!mallard}
\printindex
\end{document}
第一次运行 LaTeX 时,将创建一个扩展名为的文件.idx
,运行结束时该文件包含:
\indexentry{duck|textbf}{1}
\indexentry{zebra}{1}
\indexentry{stripy|see{zebra}}{1}
\indexentry{aardvark}{2}
\indexentry{zebra}{2}
\indexentry{Rise and Fall of Duck Empire@\emph{The Rise and Fall of the Duck Empire}}{2}
\indexentry{zebra}{3}
\indexentry{duck}{3}
\indexentry{aardvark}{3}
\indexentry{duck!mallard}{3}
这是默认格式,makeindex
但可以使用以下文件明确设置.ist
:
actual '@'
arg_close '}'
arg_open '{'
encap '|'
keyword '\\indexentry'
level '!'
还有一些其他输入说明符。(参见指数编制与处理.) 这些说明符能够makeindex
正确解析输入文件。
输出说明符指示makeindex
如何格式化输出。如果运行makeindex
上述示例,则生成的.ind
文件将如下所示:
\begin{theindex}
\item aardvark, 2, 3
\indexspace
\item duck, \textbf{1}, 3
\subitem mallard, 3
\indexspace
\item \emph{The Rise and Fall of the Duck Empire}, 2
\indexspace
\item stripy, \see{zebra}{1}
\indexspace
\item zebra, 1--3
\end{theindex}
这将使用默认输出说明符,其中包括:
preamble "\\begin{theindex}\n"
postamble "\n\n\\end{theindex}\n"
group_skip "\n\n \\indexspace\n"
item_0 "\n \\item "
item_1 "\n \\subitem "
delim_0 ", "
delim_1 ", "
.ind
现在可以通过 LaTeX 输入此文件(通过\printindex
)。生成的索引如下所示:
如果我想在每个字母组的开头添加标题,我可以创建一个名为的文件,test.ist
其中包含:
headings_flag 1
heading_prefix " \\item\\textbf{"
heading_suffix "}\n \\indexspace\n"
现在我需要运行makeindex
它将-s test.ist
把以下内容写入文件.ind
:
\begin{theindex}
\item\textbf{A}
\indexspace
\item aardvark, 2, 3
\indexspace
\item\textbf{D}
\indexspace
\item duck, \textbf{1}, 3
\subitem mallard, 3
\indexspace
\item\textbf{R}
\indexspace
\item \emph{The Rise and Fall of the Duck Empire}, 2
\indexspace
\item\textbf{S}
\indexspace
\item stripy, \see{zebra}{1}
\indexspace
\item\textbf{Z}
\indexspace
\item zebra, 1--3
\end{theindex}
下一次运行 LaTeX 将会生成索引:
之所以《鸭子帝国的兴衰》这个条目被列在“R”类而不是“T”类,是因为我把这个条目的排序键设置为“鸭子帝国的兴衰”。
xindy
样式格式 ( .xdy
)
与 不同makeindex
,xindy
具有模块,可以加载其他模块,因此您可以在现有样式的基础上进行构建。此外,xindy
具有--input-markup
( -I
) 命令行开关,用于指示输入标记。支持的标记设置有三种:latex
、omega
和xindy
。
xindy -I latex
使用texindy
相当于xindy
使用和 使用启用解析使用默认输入说明符编写的文件-I latex
的模块来调用。因此,例如,上述由 LaTeX 创建的文件可以直接由 处理。如果调用该文件,则将创建一个包含以下内容的文件:xindy
makeindex
.idx
texindy
test.idx
texindy test.idx
.ind
\begin{theindex}
\providecommand*\lettergroupDefault[1]{}
\providecommand*\lettergroup[1]{%
\par\textbf{#1}\par
\nopagebreak
}
\lettergroup{A}
\item aardvark, 2, 3
\indexspace
\lettergroup{D}
\item duck, \textbf{1}, 3
\subitem mallard, 3
\indexspace
\lettergroup{R}
\item \emph{The Rise and Fall of the Duck Empire}, 2
\indexspace
\lettergroup{S}
\item stripy, \see{zebra}{}
\indexspace
\lettergroup{Z}
\item zebra, 1--3
\end{theindex}
.ind
这与创建的文件类似,makeindex
只是它用于\lettergroup
标记类别标题。如果尚未定义此命令,则将通过文件\providecommand
开头的进行定义.ind
。如果您想更改标题的格式,只需在\lettergroup
之前定义 即可\printindex
。这使得它比上面显示的示例更简单,makeindex
该示例需要自定义.ist
文件才能显示标题。
编写xindy
模块相当复杂,在这个(已经很长的)答案中讨论起来太长了,但是xindy
常问问题给出了介绍。但是,有许多模块满足了xindy
常见需求,特别是语言模块。这些模块位于泰克思/xindy/modules/
在哪里泰克思是 TEXMF 树的基础。语言模块位于泰克思/xindy/modules/lang/
-L
并通过命令行选项进行识别。
假设我的.idx
文件现在看起来像这样:
\indexentry{ænder|textbf}{1}
\indexentry{zebra}{1}
\indexentry{aardvark}{2}
\indexentry{zebra}{2}
\indexentry{zebra}{3}
\indexentry{ænder}{3}
\indexentry{aardvark}{3}
\indexentry{ænder!gråand}{3}
makeindex
创建以下.ind
文件:
\begin{theindex}
\item aardvark, 2, 3
\indexspace
\item zebra, 1--3
\indexspace
\item ænder, \textbf{1}, 3
\subitem gråand, 3
\end{theindex}
这里makeindex
将“ænder”放在了“zebra”后面。如果这是您语言的正确位置,乍一看可能还不错,但现在尝试通过创建.ist
包含以下内容的文件来添加标题:
headings_flag 1
heading_prefix " \\item\\textbf{"
heading_suffix "}\n \\indexspace\n"
采用这种风格运行makeindex
会导致:
\begin{theindex}
\item\textbf{A}
\indexspace
\item aardvark, 2, 3
\indexspace
\item\textbf{Z}
\indexspace
\item zebra, 1--3
\indexspace
\item\textbf{Ã}
\indexspace
\item Ênder, \textbf{1}, 3
\subitem gråand, 3
\end{theindex}
UTF8 字符已变得混乱,因为makeindex
只抓取了 æ 的第一个八位字节作为标题。这破坏了文件编码。
理论上,如果我想使用,我需要使用开关(在本例中为)texindy
指定语言,并使用开关(在本例中为)指定编码。不幸的是,这会导致错误:-L
-L danish
-C
-C utf8
(require "tex/inputenc/utf8.xdy")
ERROR: Could not find file "tex/inputenc/utf8.xdy" !
并且没有.ind
生成任何文件。
如果我使用,错误就会消失-M lang/danish/utf8
。这会导致文件.ind
包含:
\begin{theindex}
\providecommand*\lettergroupDefault[1]{}
\providecommand*\lettergroup[1]{%
\par\textbf{#1}\par
\nopagebreak
}
\lettergroup{A}
\item aardvark, 2, 3
\item ænder, \textbf{1}, 3
\subitem gråand, 3
\indexspace
\lettergroup{Z}
\item zebra, 1--3
\end{theindex}
将“ænder”放入“A”字母组中(这对于丹麦字母表来说是不正确的,请参阅下面的评论)。
将.idx
文件转换为上面显示的格式有些困难。以下 XeLaTeX 文档运行良好:
\documentclass{article}
\usepackage{fontspec}
\usepackage{makeidx}
\makeindex
\begin{document}
Ænder\index{ænder|textbf}
Zebra\index{zebra}
\newpage
Aardvark\index{aardvark}
Zebra\index{zebra}
\newpage
Zebra\index{zebra}
Ænder\index{ænder}
Aardvark\index{aardvark}
Gråand\index{ænder!gråand}
\printindex
\end{document}
等效的 LaTeX 文档:
\documentclass{article}
\usepackage[utf8]{inputenc}
\usepackage[T1]{fontenc}
\usepackage[danish]{babel}
\usepackage{makeidx}
\makeindex
\begin{document}
Ænder\index{ænder|textbf}
Zebra\index{zebra}
\newpage
Aardvark\index{aardvark}
Zebra\index{zebra}
\newpage
Zebra\index{zebra}
Ænder\index{ænder}
Aardvark\index{aardvark}
Gråand\index{ænder!gråand}
\printindex
\end{document}
生成:
\indexentry{\IeC {\ae }nder|textbf}{1}
\indexentry{zebra}{1}
\indexentry{aardvark}{2}
\indexentry{zebra}{2}
\indexentry{zebra}{3}
\indexentry{\IeC {\ae }nder}{3}
\indexentry{aardvark}{3}
\indexentry{\IeC {\ae }nder!gr\IeC {\r a}and}{3}
这让人困惑texindy
。
xindy -I xindy
通过xindy
输入标记,该.idx
文件具有以下格式的条目:
(indexentry :tkey (("sort" "term") ) :locref "location" :attr "attribute" )
其中sort
,是比较函数在排序时使用的文本,term
是条目在文件中的排版方式.ind
,location
是此条目的关联位置(页码),attribute
是关联属性。这是glossaries
与 package 选项一起使用时xindy
。
通过检查使用该包创建的文件,可以说明makeindex
和所使用的语法之间的差异。xindy
glossaries
考虑以下 LaTeX 文档:
\documentclass{article}
\usepackage[utf8]{inputenc}
\usepackage[T1]{fontenc}
\usepackage[danish]{babel}
\usepackage[index,style=indexgroup]{glossaries}
\makeglossaries
\newterm[name={æ}nder]{aender}
\newterm{zebra}
\newterm{aardvark}
\newterm[parent=aender,name=gråand]{graand}
\begin{document}
\Gls[format=textbf]{aender}
\Gls{zebra}
\newpage
\Gls{aardvark}
\Gls{zebra}
\newpage
\Gls{zebra}
\Gls{aender}
\Gls{aardvark}
\Gls{graand}
\printindex
\end{document}
这类似于前面的makeidx
示例。默认情况下,本文档假定makeindex
将使用。这将创建.idx
包含以下内容的文件:
\glossaryentry{{æ}nder?\glossentry{aender}|setentrycounter[]{page}\textbf}{1}
\glossaryentry{zebra?\glossentry{zebra}|setentrycounter[]{page}\glsnumberformat}{1}
\glossaryentry{aardvark?\glossentry{aardvark}|setentrycounter[]{page}\glsnumberformat}{2}
\glossaryentry{zebra?\glossentry{zebra}|setentrycounter[]{page}\glsnumberformat}{2}
\glossaryentry{zebra?\glossentry{zebra}|setentrycounter[]{page}\glsnumberformat}{3}
\glossaryentry{{æ}nder?\glossentry{aender}|setentrycounter[]{page}\glsnumberformat}{3}
\glossaryentry{aardvark?\glossentry{aardvark}|setentrycounter[]{page}\glsnumberformat}{3}
\glossaryentry{{æ}nder?\glossentry{aender}!gråand?\subglossentry{1}{graand}|setentrycounter[]{page}\glsnumberformat}{3}
这使用\glossaryentry
而不是\indexentry
并且封装字符是?
而不是@
,因此glossaries
创建一个makeindex
.ist
包含以下内容的文件:
actual '?'
encap '|'
level '!'
quote '"'
keyword "\\glossaryentry"
preamble "\\glossarysection[\\glossarytoctitle]{\\glossarytitle}\\glossarypreamble\n\\begin{theglossary}\\glossaryheader\n"
postamble "\%\n\\end{theglossary}\\glossarypostamble\n"
group_skip "\\glsgroupskip\n"
item_0 "\%\n"
item_1 "\%\n"
item_2 "\%\n"
item_01 "\%\n"
item_x1 "\\relax \\glsresetentrylist\n"
item_12 "\%\n"
item_x2 "\\relax \\glsresetentrylist\n"
delim_0 "\{\\glossaryentrynumbers\{\\relax "
delim_1 "\{\\glossaryentrynumbers\{\\relax "
delim_2 "\{\\glossaryentrynumbers\{\\relax "
delim_t "\}\}"
delim_n "\\delimN "
delim_r "\\delimR "
headings_flag 1
heading_prefix "\\glsgroupheading\{"
heading_suffix "\}\\relax \\glsresetentrylist "
symhead_positive "glssymbols"
numhead_positive "glsnumbers"
page_compositor "."
suffix_2p ""
suffix_3p ""
另一方面,如果xindy
您在加载时添加了包选项glossaries
:
\usepackage[index,xindy]{glossaries}
该.idx
文件现在如下所示:
(indexentry :tkey (("{æ}nder" "\\glossentry{aender}") ) :locref "{}{1}" :attr "pagetextbf" )
(indexentry :tkey (("zebra" "\\glossentry{zebra}") ) :locref "{}{1}" :attr "pageglsnumberformat" )
(indexentry :tkey (("aardvark" "\\glossentry{aardvark}") ) :locref "{}{2}" :attr "pageglsnumberformat" )
(indexentry :tkey (("zebra" "\\glossentry{zebra}") ) :locref "{}{2}" :attr "pageglsnumberformat" )
(indexentry :tkey (("zebra" "\\glossentry{zebra}") ) :locref "{}{3}" :attr "pageglsnumberformat" )
(indexentry :tkey (("{æ}nder" "\\glossentry{aender}") ) :locref "{}{3}" :attr "pageglsnumberformat" )
(indexentry :tkey (("aardvark" "\\glossentry{aardvark}") ) :locref "{}{3}" :attr "pageglsnumberformat" )
(indexentry :tkey (("{æ}nder" "\\glossentry{aender}") ("gråand" "\\subglossentry{1}{graand}") ) :locref "{}{3}" :attr "pageglsnumberformat" )
扩展的拉丁字符(例如 å)没有像前面的makeidx
示例那样被扩展,因为默认情况下,它们glossaries
会“净化”排序键。(在 æ 周围使用括号的原因在 UTF8 部分中进行了讨论mfirstuc
手动的。
这次,不是创建附带.ist
文件,而是glossaries
创建一个xindy
.xdy
相当大的文件,并且太大了,无法在此重现,而不会超出 StackExchange 答案的最大长度。但是,如果您亲自尝试上述示例,您将能够看到语法差异。
运行 Perl 脚本makeglossaries test
(示例文件名为test.tex
)相当于运行xindy
以下命令:
xindy -L danish -C utf8 -I xindy -M "test" -t "test.ilg" -o "test.ind" "test.idx"
尽管-L danish -C utf8
已使用,但现在不会产生先前的错误,因为texindy
不再xindy
尝试输入tex/inputenc/utf8.xdy
。索引现在如下所示:
再次,切换到 XeLaTeX 可以使文档更简单:
\documentclass{article}
\usepackage{fontspec}
\usepackage{polyglossia}
\setmainlanguage{danish}
\usepackage[index,style=indexgroup,xindy]{glossaries}
\makeglossaries
\newterm{ænder}
\newterm{zebra}
\newterm{aardvark}
\newterm[parent=ænder]{gråand}
\begin{document}
\Gls[format=textbf]{ænder}
\Gls{zebra}
\newpage
\Gls{aardvark}
\Gls{zebra}
\newpage
\Gls{zebra}
\Gls{ænder}
\Gls{aardvark}
\Gls{gråand}
\printindex
\end{document}