Latex 默认显示命令值 - 我发现显示命令名称和值更加困难。
我有一个命令列表,我想循环并打印每个命令的名称和值。
\documentclass[11pt,letterpaper]{article}
\usepackage{tikz} % defines foreach
\begin{document}
\def\one{this is one}
\def\two{this is two}
\def\three{this is three}
\def\CMDs{\one,\two,\three} % list of commands I would like to loop over
\foreach \cmd in \CMDs
{
\string\cmd = \cmd \\ % should be name = value
}
\end{document}
但是它\string
没有解析 \cmd,它只是打印 cmd。
甚至\expandafter\string\csname\cmd\endcsname = \cmd
按照建议尝试过这里- 没有用,它正在扩大并打印两边的值,而不是名称。
请就如何实现这一点提供建议。
如果有人想了解背景,这是我的简历制作器项目 - 跟踪内部变量并根据需要转储其值,作为包用户的调试辅助。
答案1
幸运的是,这\cmd
是一个包含目标宏的宏,因此\expandafter
解决了这个问题,它扩展\cmd
并显示目标宏为\string
:
\documentclass[11pt,letterpaper]{article}
\usepackage[T1]{fontenc}% to get correct backslash
\usepackage{tikz} % defines foreach
\begin{document}
\def\one{this is one}
\def\two{this is two}
\def\three{this is three}
\def\CMDs{\one,\two,\three} % list of commands I would like to loop over
\foreach \cmd in \CMDs
{
\expandafter\string\cmd = \cmd\par % should be name = value
}
\end{document}
进一步说明:
您可以通过以下方式检查宏定义
\show
,例如:\show\cmd
TeX 停止并在控制台上显示含义后:> \cmd=macro: ->\one .
另一种方法是
\meaning
。它的工作原理类似于\string
,但它不是将标记转换为字符串,而是将标记的含义转换为字符串,例如:\typeout{\string\cmd=\meaning\cmd}%
打印到控制台/
.log
文件:\cmd=macro:->\one \cmd=macro:->\two \cmd=macro:->\three
如果
\cmd
将通过分配\let
,例如:\let\cmd=\one
则与
\cmd
相同。并且 名称不能再从 派生而来。\meaning
\one
\one
\cmd
答案2
这是一个灵活的实现,您可以选择显示命令含义的模式。
\documentclass{article}
\usepackage{xparse}
\ExplSyntaxOn
% The user level command just hands its arguments to an inner function
% #1 is optional, default value empty; #2 is the list of commands
\NewDocumentCommand{\showcommands}{O{}m}
{
\gopa_show_commands:nn { #1 } { #2 }
}
\cs_new_protected:Npn \gopa_show_commands:nn #1 #2
{
% start a group so changes to the meaning of functions
% deriving from the key setting will be undone at the end
\group_begin:
% evaluate the first argument, which should be `mode=<value>'
\keys_set:nn { gopa/commands } { #1 }
% for each item in the second argument (represented by ##1)
% execute the code below
\clist_map_inline:nn { #2 }
{
{\ttfamily \token_to_str:N ##1~=~\gopa_show_mode:N ##1 }
\par
}
\group_end:
}
% a variant for `mode=expand'; \use:n just uses its argument
% so \use:V will expand the control sequence that follows it
% and brace the expansion, so \use:n will remove the braces
\cs_generate_variant:Nn \use:n { V }
% Set up the key/value pairs; just one key that can receive
% the values "show", "expand" or "meaning"; default is "expand"
\keys_define:nn { gopa/commands }
{
mode .choice:,
mode / show .code:n = \cs_set_eq:NN \gopa_show_mode:N \cs_show:N,
mode / expand .code:n = \cs_set_eq:NN \gopa_show_mode:N \use:V,
mode / meaning .code:n = \cs_set_eq:NN \gopa_show_mode:N \cs_meaning:N,
mode .initial:n = expand,
}
\ExplSyntaxOff
\begin{document}
\def\one{this is one}
\def\two{this is two}
\def\three{this is three}
\showcommands{\one,\two,\three}
\showcommands[mode=meaning]{\one,\mbox}
\end{document}
另一个可能的选择是mode=show
使用终端显示命令的含义。mode=meaning
当列表中的命令之一不是无参数宏时使用。