使用 expl3 处理多个变量

使用 expl3 处理多个变量

这是最有可能分为几部分的问题的第三部分,第一部分已经得到回答这里,第二个得到了回答这里。现在我已经开始expl3在文档中更广泛地使用它,我想知道如何在新的文档命令中使用多个变量。例如,我正在使用的示例是尝试编写一个最终将归于平方根根的表达式。给出:

\documentclass[12pt]{article}
\usepackage{xfp}
\ExplSyntaxOn
\NewDocumentCommand{\underradical}{}
 {
  % Attempting: Setting a value to correspond to || or nothing
  \int_set:Nn \l_tmpa_int_abs { \int_rand:nn { 1 } { 2 } }
  % if odd indicator, use |, else do nothing
  \int_if_odd:nTF \l_tmpa_int_abs { | } {}
  % the variable
  x
  % Attempting: Setting a variable to correspond to an x shift or not
  \int_set:Nn \l_tmpa_int_val { \int_rand:nn { 1 } { 2 } }
  % Attempting: Setting a variable to correspond to a left or right shift
  \int_set:Nn \l_tmpa_int_dir { \int_rand:nn { 1 } { 2 } }
  % a random sign
  \int_if_odd:nTF \l_tmpa_int_val {
                                    \int_if_odd:nTF \l_tmpa_int_dir { + } { - }
                                    } {}
  % the absolute value of the summand
  \int_if_odd:nTF \l_tmpa_int_val { \int_rand:nn { 1 } { 3 } }
  % if odd exponent use |, else do nothing
  \int_if_odd:nTF \l_tmpa_int_abs { | } {}
 }
 
\ExplSyntaxOff

\begin{document}
\underradical
\end{document}

这里使用了三个不同的变量,\l_tmpa_int_abs\l_tmpa_int_val\l_tmpa_int_dir。然而,这并没有产生期望的输出,它给出的输出是 2x22 或 1x22,或者任何组合,其中每个 2 也有相等的可能性成为 1。我以为我根据第 3 页和第 4 页正确地实现了命名方案expl3 文档,但显然这不太可能,因为我的输出不正确。我至少可以让其中一个 2 或 1 实际打印为所需的符号或数字,但前提是我将它们的变量更改为\l_tmpa_int。当然,我无法让所有三个变量都声明为这样,因为编译器不知道我指的是哪一个。我想知道如何在给定的新文档命令中使用多个变量,以便我修复我的问题。

答案1

三个观察结果:

  1. 您必须使用\..._new:N(在您的情况下\int_new:N) 或类似函数声明所使用的所有变量。 (这不是必需的,\l_tmpa_int因为该变量已在 expl3 中预定义。)

  2. 命名方案的末尾是变量的类型,中间是名称。因此,eg\l_tmpa_int_abs有类型int,因此可以更好地命名为\l_underradical_abs_int。(其中可以是任何标识模块的名称。)如果变量具有定义的函数,则underradical无需命名变量。(代表tmpatmpa议员变量A,如果您不想声明“正确”的名称,它可以用于命名临时使用的预定义变量)

  3. \int_if_odd:nTF \l_tmpa_int_val { \int_rand:nn { 1 } { 3 } }
    

    缺少 false 块。您可以通过{}在行尾添加(或其他代码)来修复此问题,或者,如果块本来就是空的,则可以使用\int_if_odd:nT。(对于以结尾的条件宏,对于其他分支应该为空的情况TF,有相应的宏仅以T或结尾F。)

应用所有这三点将导致

\documentclass[12pt]{article}
\usepackage{xfp}
\ExplSyntaxOn
\int_new:N \l_underradical_abs_int
\int_new:N \l_underradical_val_int
\int_new:N \l_underradical_dir_int
\NewDocumentCommand{\underradical}{}
 {
  % Attempting: Setting a value to correspond to || or nothing
  \int_set:Nn \l_underradical_abs_int { \int_rand:nn { 1 } { 2 } }
  % if odd indicator, use |, else do nothing. Yould use \int_if_odd:nT,
  % I left \int_if_odd:nTF to show that this works too
  \int_if_odd:nTF \l_underradical_abs_int { | } {}
  % the variable
  x
  % Attempting: Setting a variable to correspond to an x shift or not
  \int_set:Nn \l_underradical_val_int { \int_rand:nn { 1 } { 2 } }
  % Attempting: Setting a variable to correspond to a left or right shift
  \int_set:Nn \l_underradical_dir_int { \int_rand:nn { 1 } { 2 } }
  % a random sign
  \int_if_odd:nT \l_underradical_val_int {
    \int_if_odd:nTF \l_underradical_dir_int { + } { - }
  }
  % the absolute value of the summand
  \int_if_odd:nT \l_underradical_val_int { \int_rand:nn { 1 } { 3 } }
  % if odd exponent use |, else do nothing
  \int_if_odd:nT \l_underradical_abs_int { | }
 }
 
\ExplSyntaxOff

\begin{document}
\underradical
\end{document}

相关内容