我只是想要一种好方法来制作反斜杠字符(或任何给定格式用作转义字符的任何字符),适合\write
文件或传递给 pdfTeX 原语。
我要强调的是,排版是不是问题的关键。事实上,如果使用 cmr10/11/12,我想要的不会可以用来排版反斜杠,因为这些字体由于某种原因将该插槽用于其他用途。
一个可以接受的答案会告诉你一般如何做到这一点,而不仅仅是在 LaTeX 中,尽管特定于格式的技术也很有趣(并且会被投票赞成)。
解释如何对所有具有特殊 catcode 的角色执行此操作可获得加分。(不是字面上的加分,只是比喻性的加分。至少不是我给的;我目前只有 296 个声望!)
答案1
做这种事情的另一种方法是使用一个\lccode
技巧:
\begingroup\lccode`!=`\\\lowercase{\endgroup\def\@backslashchar{!}}
由于 的特殊属性,这避免了更改 catcodes 的任何需要\lowercase
。与方法相比\expandafter\@gobble\string
,它更灵活一些,因为您可以在宏中选择结果字符的 catcode。与更改 catcodes 相比,您不必使用 ,\global
因为 是如何\lowercase
与 交互的\endgroup
。
以下是代码的详细信息。\begingroup
此处用于将 lccode 更改保留在本地。
\lccode`!=`\\
意味着当小写时,!
您将获得反斜杠\
(选择!
是任意的,您只需要normal
在 内不会出现在 中的其他地方的字符即可\lowercase
)。重要的是,小写版本的!
将是普通字符,因为\lowercase
不会更改 catcodes。
因此,该代码\lowercase{\endgroup\def\@backslashchar{!}}
相当于\endgroup\def\@backslashchar{\}
但\
并不特殊(因此\
后面}
不会被解释为\}
而是两个独立的实体)。
最后,结果是您已将定义\@backslashchar
为具有\
正常 catcode 的。因此,它可以在命令内部使用\write
,而不会引起与此相同的问题\
。
此 lccode 技巧适用于所有其他特殊字符。例如,如果您想要一个空格字符(当然,对于空格,宏\space
可以正常工作):
\begingroup\lccode`!=`\ \lowercase{\endgroup\def\@spacechar{!}}
如果你将代码拆分成两行,只要小心行尾并在%
后面添加一个\
:
\begingroup\lccode`!=`\ %
\lowercase{\endgroup\def\@spacechar{!}}
答案2
有很多方法可以做到这一点,具体取决于您想要做什么。您并不总是需要更改catcode
。以下是一些示例:
\textbackslash
将简单排版\
要将宏写入文件,请使用\string\macro
。这也可以用于排版。
您还可以使用以下方式定义它:
\newcommand{\bs}{\symbol{'134}} % a backslash in tt type in OT1/T1
其他海报已经解释了这个\lccode
技巧和变化\catcode
,而我没有添加它。
并且最少有这些:
\documentclass[11pt]{article}
\begin{document}
\newcommand{\bs}{\symbol{'134}}% a backslash in tt type in OT1/T1
\newcommand{\BS}{\texttt{\symbol{`\\}}}
\BS, \texttt{\string\test}, \texttt{\bs}
\end{document}
答案3
这是更改 catcodes 的一种可能方法(刚刚看到 TH. 提出了几乎相同的建议这个答案):
\begingroup
\catcode`\@=0
\catcode`\\=11
@global@def@backslash{\}
@endgroup
请注意,我首先给出了@
catcode 0,以便我可以用它来代替\
。对于其他特殊字符,实际上更容易;您不需要@
。
正如 Philippe 指出的,上述方法的缺点是使用了\global
。下面是另一个避免这种情况的好技巧:
\begingroup
\catcode`\@=0
\catcode`\\=11
@def@makeliteralbackslash{@def@backslash{\}}
@expandafter@endgroup@makeliteralbackslash
宏@makeliteralbackslash
已展开前团体的结束;一扩展发生在 catcode 更改仍然有效时。然后其自身的定义\backslash
在组外执行。我并不是说这是最好的方法:它只是举一个有趣的 TeX 核心技巧的例子。
答案4
expl3 解决方案,以备将来有人遇到这种情况时参考。
\iow_char:N \\
从语义上讲,使用iow
函数进行书写是有意义的;尽管无法保证扩展步骤的数量等,或者您实际上是否获得了 catcode-other 反斜杠标记。
(即从技术上来说,catcode 字母/对齐/数学上标/数学下标\write
也适用于,尽管这样做是一个相当奇怪的选择)
\cs_to_str:N \\
实际上,(至少在我的版本中)\iow_char:N
与 相同\cs_to_str:N
。这将通过 2 个扩展步骤扩展为结果。
\char_generate:nn {`\\} {12}
再次保证在 2 个扩展步骤中扩展为 catcode-other 反斜杠标记。