SE,最近我在玩弄expl3
一些xparse
,遇到了以下问题:我想创建一个创建新命令的命令——类似于这个帖子。这并不难,只要第二个命令没有任何参数;尝试创建一个接受参数的命令就有点棘手。
我目前得到的:
\documentclass{article}
\usepackage{xparse}
\NewDocumentCommand\test{ m}
{
\NewDocumentCommand#1 {m}
{My name is \string#1, king of kings}
}
\begin{document}
\test{\ozymandias}
\ozymandias{\manthano}
\end{document}
输出结果My name is ozymandias, king of kings
为,给出了正确的十四行诗,但不是我想要的。我知道问题出在哪里,只是不知道如何修复它 :)
答案1
我对\string#1
里面的情况感到好奇。
里面的新命令可以用以下方式构造
\expandafter\NewDocumentCommand\csname #1\endcsname{...}{....}
即必须先构造新序列的名称\expandafter
(先给出名称,然后执行操作)。对于传统的或等,\NewDocumentCommand
必须采取相同的方法。\newcommand
\renewcommand
但是,\test
命令必须以 的形式使用\test{ozymandias}
,不带\
!
请注意,必须使用##1
来访问内部宏的第一个参数(如果需要的话),后续参数用##2
等编号。
\documentclass{article}
\usepackage{xparse}
\NewDocumentCommand{\manthano}{}{Manthano}
\NewDocumentCommand\test{ m}
{%
\expandafter\NewDocumentCommand\csname #1\endcsname{m}{%
My name is ##1, king of kings%
}
}
\begin{document}
\test{ozymandias}
\ozymandias{\manthano}
\end{document}
编辑:要使用\test
,\
您必须调整命令以
\makeatletter
\NewDocumentCommand\test{ m}
{%
\expandafter\NewDocumentCommand\csname\expandafter\@gobble\string #1\endcsname{m}{%
My name is ##1, king of kings%
}
}
\makeatother