我正在尝试在文件中输出一些文本。我使用过filecontents
,效果很好。但是,如果我将filecontents
环境放在宏中,则调用宏时它只会输出注释,而不会输出文本。
以下是一个例子:
\documentclass{article}
\usepackage{filecontents}
\usepackage{etoolbox}
\begin{filecontents}{\jobname.abc}
this gets in the file
}
\end{filecontents}
\newcommand{\toto}{
\begin{filecontents}{\jobname.def}
this won't...
\end{filecontents}
}
\begin{document}
\toto
\end{document}
我也尝试在钩子filecontents
中使用\AtEndDocument
,但文件中仍然没有找到任何内容。为此,我在上述代码的序言中添加了
\AtEndDocument{
\typeout{AtEndDocument is being executed}
\begin{filecontents}{\jobname.ghi}
this won't either...
\end{filecontents}
}
在这三种情况下,我都会收到警告,提示文件已被创建/替换:
LaTeX Warning: Overwriting file xxx.ghi
有人知道发生了什么吗?如何纠正这个问题,以便内容可以进入文件?
答案1
最好创建一个输出流,将内容附加到其中;newfile
提供此功能:
\documentclass{article}
\usepackage{filecontents,newfile}
\begin{filecontents*}{\jobname.abc}
this gets in the file \jobname.abc
\end{filecontents*}
\newoutputstream{mystream}
\openoutputfile{\jobname.def}{mystream}
\newcommand{\toto}{%
\addtostream{mystream}{this will be written to \jobname.def.}%
}
\begin{document}
Some text. \toto
\end{document}
书面文件 -\jobname.abc
和\jobname.def
- 包含以下内容:
latex_stuff.abc
这进入文件 latex_stuff.abc。
latex_stuff.def
这将被写入 latex_stuff.def。
答案2
失败的原因有多种。
第一个也是最重要的原因:当 token 被吸收作为另一个命令的参数时,包括 \newcommand
和\AtEndDocument
,它们接收其类别代码(如果不是控制序列)并且结束行被转换为空格或\par
标记。
在\begin{filecontents}
处理时,会进行几项更改,这些更改与发生的情况非常相似verbatim
(并不完全相同);例如,您不希望反斜杠保持其通常的含义,也不希望将结束行转换为空格。
因此,\end{filecontents}
TeX 寻找的闭包是不是15 个代币
\end • { f • i • l • e • c • o • n • t • e • n • t • s • }
但 18:
\ • e • n • d • { f • i • l • e • c • o • n • t • e • n • t • s • }
其中反斜杠和括号的类别代码为 12;实际上查找还包括结束行(必须是活动字符,具有非常特殊的含义)。
还有其他一些问题,特别是与非 ASCII 字符相关的问题。
这个问题能被纠正吗?一般来说不能。
您可能并不需要filecontents
,因为在处理开始或结束时写入具有给定内容的文件应该没有任何区别。因此,您可能正在寻找错误的工具来实现您想要的功能。