答案1
-specifiero
是“低级”的,并且只对参数进行一次扩展:\foo:o {...}
相当于\expandafter \foo:n \expandafter {...}
。相比之下,V
-type 扩展提供了价值变量,可以是tl
/ clist
(存储为宏)或int
/ dim
/ skip
(存储为寄存器)。为了处理后者,V
-type 扩展会插入所需的内容\the
以产生值。因此,o
-type 扩展仅在您知道要扩展的值是宏的情况下才等同于-type。在-type 不适用的情况下,V
可以使用-type 扩展,例如o
V
\foo:n { \use_none:n <some tokens> }
请注意o
-type 采用平衡文本参数(括号中为零个或多个标记),而V
-type 只接受一个标记。这在语义上有很大不同。
答案2
o
表示“扩大一级”。
V
表示“获取值”。
虽然这可能tl
对或变量产生相同的结果clist
,但其他变量则并非如此。
int
让我们尝试一个玩具问题,即从存储在任何变量中或明确给出的整数中提取最高有效位。
\ExplSyntaxOn
\NewExpandableDocumentCommand{\msd}{sm}
{% \msd* takes a variable
\IfBooleanTF{#1}
{
\aad_msd:V #2
}
{
\aad_msd:n { #2 }
}
}
\cs_new:Nn \aad_msd:n
{
\__aad_msd:w #1 \q_stop
}
\cs_generate_variant:Nn \aad_msd:n { V,o }
\cs_new:Npn \__aad_msd:w #1 #2 \q_stop { #1 }
\int_new:N \l_aad_test_a_int
\int_set:Nn \l_aad_test_a_int { 1234 }
\int_const:Nn \c_aad_test_b_int {4321}
\tl_set:Nx \l_tmpa_tl { \msd{4321} } \tl_show:N \l_tmpa_tl
\tl_set:Nx \l_tmpa_tl { \msd*{\l_aad_test_a_int} } \tl_show:N \l_tmpa_tl
\tl_set:Nx \l_tmpa_tl { \msd*{\c_aad_test_b_int} } \tl_show:N \l_tmpa_tl
\ExplSyntaxOff
如果你尝试一下,你会得到
> \l_tmpa_tl=4.
> \l_tmpa_tl=1.
> \l_tmpa_tl=4.
现在替换\aad_msd:V #2
为\aad_msd:o { #2 }
,你会得到
> \l_tmpa_tl=4.
> \l_tmpa_tl=\l_aad_test_a_int .
> \l_tmpa_tl=\c_aad_test_b_int .
你看到发生了什么吗?整数变量不可扩展,因此不会对它们执行任何操作。与寄存器相对应的所有变量也是:o
如此:dim
,,。skip
muskip