我想以十六进制形式打印一些 256 位长的哈希值(因此是 64 个字符,我跳过了通常的“0x”,没有空格或标点符号)并使用等宽字体。
因此,我首先选择了 \texttt,它不会对我的字符串进行连字符处理。我看到了一些有趣的答案,例如如何打破较长的 \texttt 部分和特定字符自动换行但是它们都为特定字符定义了换行符,并且我发现如果没有某种自然循环就对十六进制的 16 个字符中的每一个使用它们的技巧会很难看。
有没有办法定义一个命令,使得里面的文本将被输入为 texttt 但在任何字符上中断,或者更好的是,有一种标准的方式来排版长十六进制字符串,并考虑到这个问题?
梅威瑟:
\documentclass{article}
\newcommand{\hash}[1]{\texttt{#1}}%In a perfect world, this would be changed to allow linebreaks anywhere in #1
\begin{document}
SHA-256 is a hash function with a 256-bit long output: \hash{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
\end{document}
答案1
已经有一个用于此的包:
\documentclass{article}
\usepackage{seqsplit}
\newcommand{\hash}[1]{{\ttfamily\seqsplit{#1}}}
\begin{document}
SHA-256 is a hash function with a 256-bit long output:
\hash{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
\end{document}
不含包装:
\documentclass{article}
\ExplSyntaxOn
\NewDocumentCommand{\hash}{O{\ttfamily}m}
{
\group_begin:
#1 % font choice, default \ttfamily
\tl_map_function:nN { #2 } \__anab_hash_char:n
\group_end:
}
\cs_new:Nn \__anab_hash_char:n { #1 \skip_horizontal:n { 0pt plus 0.2pt } }
\ExplSyntaxOff
\begin{document}
SHA-256 is a hash function with a 256-bit long output:
\hash{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
\noindent\parbox[t]{0.4\textwidth}{%
SHA-256 is a hash function with a 256-bit long output:
\hash{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
}\quad
\parbox[t]{0.4\textwidth}{%
SHA-256 is a hash function with a 256-bit long output:
\hash[\sffamily]{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
}
\end{document}
答案2
你可以在每个字符后添加一个惩罚
\documentclass{article}
\newcommand{\hash}[1]{\texttt{\zz#1\zz}}%In a perfect world, this would be changed to allow linebreaks anywhere in #1
\def\zz#1{%
\ifx\zz#1\else
#1\linebreak[1]\expandafter\zz
\fi}
\begin{document}
SHA-256 is a hash function with a 256-bit long output: \hash{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
\end{document}
答案3
解决方案让 TeX 将字符视为单词
这是可行的,但是有一个限制,即表示的字符不起作用。例如,使用十六进制(\char"02C6
)或八进制表示法。
\documentclass{article}
\def\hash#1{\xscan#1\relax}% calls xscan which looks ahead one token, #1
\def\xscan{\afterassignment\xxscan\let\token= }% assign single token to \token and call \xxscan
\def\xxscan{%
\ttfamily% set font style
\ifx\token\relax\ttfamily\else%test for end-of-line or end of group and switch to ttfamily
\ifcat\token\space%
\token% token is catcode 10
\spaceskip=.5em% remove glue from space for fixed-width space
\xspaceskip=.5em% remove glue from space for fixed-width space
\else%
\token\hskip 0pt plus 1sp minus 1sp % add glue to any non-catcode 10 (space)
\fi
\spaceskip=0pt% reset space skip
\expandafter\xscan% feed next token to \xscan, which is effectively a recursive call
\fi}
\begin{document}
SHA-256 is a hash function with a 256-bit long output: \hash{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
%SHA-256 is a hash function with a 256-bit long output: \hash{d270f\char"02C6\relax747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}% \char" denoted char syntax not supported
\end{document}
有关的:我怎样才能让 LaTeX 识别我的宏中的空格(catcode 10)?
使用字符间标记的解决方案
\XeTeXinterchartokenstate=1 % turn them on
\XeTeXinterchartoks 0 0 = {\penalty0\relax}#1} % use insert token
如果使用 TeX Live 2017 并使用,这是我的首选解决方案xelatex
。 这样做的好处是它支持 -it should-like 表示字符的原始功能\texttt
(请参阅 David Carlisle 的答案下的评论)。
\documentclass{article}
\newcommand{\hash}[1]{\texttt{\XeTeXinterchartokenstate=1\XeTeXinterchartoks 0 0 = {\penalty0\relax}#1}}%In a perfect world, this would be changed to allow linebreaks anywhere in #1
\begin{document}
SHA-256 is a hash function with a 256-bit long output: \hash{d270f747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}
SHA-256 is a hash function with a 256-bit long output: `\hash{d270f\char"02C6\relax747a8743f11aef93c10e9cb6932cc0b862464c1133dc0f8889088740d15}`
\end{document}
答案4
将其配置为 URL。已编辑,以在组内执行此操作\hexdump{}
,以便\url
不受重新定义的影响。
\documentclass{article}
\usepackage{url,lipsum}
\urlstyle{rm}
\newcommand\hexdump[1]{%
\begingroup\urlstyle{tt}%
\def\UrlBreaks{%
\do\1\do\2\do\3\do\4\do\5\do\6\do\7\do\8\do\9\do\0\do\A\do\B\do\C\do\D\do\E\do\F}%
\url{#1}\endgroup%
}
\textwidth3.34in
\parskip 1ex
\begin{document}
\noindent\hexdump{5A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC5%
A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC5A0FF349ABC}
\lipsum[1]
URLs should be unaffected: \url{www.xyz.com}
\end{document}