我创建了一个命令来动态定义矢量宏:
\newcommand{\makevec}[1]{\expandafter\def\csname #1\endcsname{\vec{#1}}}
效果和我预期的一样。但随后我尝试使用包\foreach
中定义的命令修改此命令以接受逗号分隔的符号列表pgffor
:
\newcommand{\makevec}[1]{
\foreach \name in {#1} {
\expandafter\def\csname \name\endcsname{\vec{\name}}
}
}
该命令编译时没有错误,但无法定义正确的宏。经过一番谷歌搜索后,我遇到了一些与我的问题有些类似的问题,这些问题表明问题可能与范围有关,所以我尝试了以下两种方法:
\newcommand{\makevec}[1]{
\foreach \name in {#1} {
\global\expandafter\def\csname \name\endcsname{\vec{\name}}
}
}
和
\newcommand{\makevec}[1]{
\foreach \name in {#1} {
\expandafter\xdef\csname \name\endcsname{\vec{\name}}
}
}
第一个产生的结果与我最初的解决方案相同,而第二个产生错误Argument of \reserved@a has an extra }
和Paragraph ended before \reserved@a was complete
。任何帮助都值得赞赏。
更新:这是一份最基本的文档:
\documentclass{article}
\usepackage{pgffor}
\newcommand{\makevec}[1]{
\foreach \name in {#1} {
\global\expandafter\def\csname \name\endcsname{\textbf{\name}}
}
}
\makevec{v}
\begin{document}
$\v$
\end{document}
这会undefined control sequence error
在调用时引发\v
并编译为空白文档。
答案1
你基本上是在做
\gdef\v{\textbf{\name}}
这当然会引发错误,因为\name
通常是未定义的,而且即使定义,也很可能不是“v”。如果你这样做
\makevec{v,w}
您需要定义\v
并\w
扩展为\name
。
您需要\xdef
,但\textbf
应该用 进行保护\noexpand
,为了安全起见,只展开一次\name
:
\newcommand{\makevec}[1]{%
\foreach \name in {#1} {%
\expandafter\xdef\csname\name\endcsname{\noexpand\textbf{\unexpanded\expandafter{\name}}}%
}%
}
但请注意,以这种方式重新定义命令非常危险。之后,\makevec{v}
您将无法在参考书目中添加名为 Čech 的作者,因为您已将“ \v
to”重新定义为与预期不同的意思。