如何查找 tex 文件中使用的所有包

如何查找 tex 文件中使用的所有包

假设我想要grep一个 tex 文件中使用的所有包:

$ grep usepackage my.tex

可以,但(据我所知)有一个例外:如果一个包加载了太多选项,文件的作者决定插入换行符,例如

\usepackage[option1,
option2,
option3]{thepackage}

有没有办法告诉 grep 继续解析文件直到到达}

理想情况下,我只会获得thepackageas 输出,以便我可以对其进行迭代,例如:

$ for i in `locate `my grep command`.sty`
do
grep \\\\newcommand{\\\\createstrouble} $i
done

为了快速找到\createstrouble定义命令的包?

编辑:还有一个复杂因素:我有一个\usepackage如下命令:

\usepackage[pdftitle={My Title},
 pdfauthor={My Author}]{hyperref}

编辑:我明白这种方法不适合我的目的,即找出冲突的软件包。主要是因为通过加载的软件包会\usepackage{something}拉入更多软件包RequirePackage,而这些软件包不会出现在雷达上。最好使用日志文件,可能\listfiles在前言中使用,生成已加载文件的列表,并通过texmf目录查找不同软件包使用的实际命令名称。

答案1

-P您可以在常规 grep 中使用(PCRE 模式)和-z标志的组合进行多行匹配,例如

grep -zP '(?s)\\usepackage.+?}' file

pcregrep

pcregrep -M '(?s)\\usepackage.+?}' file

(?s)修饰符允许.匹配换行符。


要获取包名称,您可以尝试

grep -zPo '(?s)\\usepackage.*?{\K.+?(?=})' file

或者

pcregrep -Mo '(?s)\\usepackage.*?{\K.+?(?=})' file


在自己的 TeX 手稿上测试简单的 grep 表达式,我得到以下软件包列表:

~$ grep -zPo '(?s)\\usepackage.*?{\K.+?(?=})' myfile.tex
geometry
changepage
inputenc
textcomp,marvosym
fixltx2e
amsmath,amssymb
cite
nameref,hyperref
lineno
microtype
rotating
setspace
caption
lastpage,fancyhdr,graphicx
epstopdf

答案2

编写 TeX 解析器并不简单。因此只能尝试以下解决方案。

使用awk两次和uniq

awk '/usepackage/,/}$/ {gsub(/\\/,"\n",$0);printf "%s",$0}' my.tex |\
awk -F{ '{gsub(/}/,"",$NF); if ($NF != "") {print $NF}}' |\
sort -u

例子

$ cat foo.tex
\usepackage[pdftitle={My Title},
 pdfauthor={My Author}]{hyperref}
\usepackage{ngerman}
\usepackage[scale=0.85]{geometry}

$ awk '/usepackage/,/}$/ {gsub(/\\/,"\n",$0);printf "%s",$0}' foo.tex |\
  awk -F{ '{gsub(/}/,"",$NF); if ($NF != "") {print $NF}}' |\
  sort -u
geometry
hyperref
ngerman

相关内容