在 Dyalog 中创建闭包向量

Ian*_*tin 5 apl dyalog

我想定义一个带有单个参数的匿名函数向量,然后在该向量上映射一个参数,返回每个索引x的结果数组。f(x)这在 Dyalog 中可能吗?

\n\n

我问这个问题是因为我天真的尝试创建这样一个闭合向量:

\n\n
fs \xe2\x86\x90 {\xe2\x8d\xb5\xc3\x972} {\xe2\x8d\xb5\xc3\x974} {\xe2\x8d\xb5\xc3\x978}\n
Run Code Online (Sandbox Code Playgroud)\n\n

行为奇怪。尝试引用fs看似引用所有索引的单个索引并导致输出混乱:

\n\n
 fs[1]\n   \xe2\x88\x87{\xe2\x8d\xb5\xc3\x972}\n \xe2\x88\x87       \xe2\x88\x87{\xe2\x8d\xb5\xc3\x974}\n \xe2\x88\x87       \xe2\x88\x87{\xe2\x8d\xb5\xc3\x978}\n \xe2\x88\x87  [ 1\n
Run Code Online (Sandbox Code Playgroud)\n\n

\xe2\x8d\xb4fs返回类似的输出而不是 3,让我相信我根本没有创建数组。解决这个问题的正确方法是什么?

\n

EKo*_*ons 5

不幸的是,这在 Dyalog 中是不可能的。您在那里所做的确实不是一个数组,而是一个fgh-fork,它是一系列函数f g h,当像 一样单子调用时(f g h)Y,其行为就像(f Y)g h Y。如果左括号 ( ) 的左边有一个函数[而不是数组,那么这不是括号索引,而是运算符。但是,轴运算符只能应用于某些原始函数,以及从/\\或派生\xe2\x8c\xbf的函数\xe2\x8d\x80应用于这样的函数,将会出现语法错误

\n\n

\xe2\x8d\xb4fsfs同样,是一个函数序列,在本例中是一个 atop,而不是像fs函数那样返回 形状的东西。

\n\n

然而,即使函数不是 APL 中的一流对象,您也可以以某种方式滥用训练,使其看起来像是参数实际上映射到函数数组中。为此,我们定义一个“ FunctionChainLink 函数:FL

\n\n
FL \xe2\x86\x90 {(\xe2\x8a\x82\xe2\x8d\xba),\xe2\x8d\xb5}\n
Run Code Online (Sandbox Code Playgroud)\n\n

因此,假设我们有函数fgh一个参数Y,并且我们想要返回(f Y)(g Y)(h Y)。现在可以写成(f FL g FL h)Y,对吗?嗯,不,有一个问题。最右边出现的FL必须替换为FL\xe2\x88\x98\xe2\x8a\x82。不幸的是,这是一个不可避免的麻烦,但至少现在你可以不用Y每次都提了。现在有两种情况:

\n\n
    \n
  • 函数数组(链)的长度为 1,即它只包含一个函数f:在这种情况下,您可以简单地使用(\xe2\x8a\x82f)Y.
  • \n
  • 函数链包含多个函数,假设fgh:现在,您将编写(f FL g FL\xe2\x88\x98\xe2\x8a\x82h)Y
  • \n
\n\n

我建议保持该函数的名称简短,最多 2 个字符,因为它会被多次使用。

\n\n

而且,这个FL功能是如何工作的?事实上,它将结果链接在一起,而不是函数本身。它只是将左侧的结果封装(\xe2\x8a\x82\xe2\x8d\xba)在一个数组中 ( ),然后将其右侧的结果连接它 ( ,\xe2\x8d\xb5)。这导致将左侧结果“前置”到右侧结果数组中,但将其保持在一起,即不分离其各个元素。\xe2\x8a\x82第一次在这样的“链”中使用它的原因是因为FL无法确定其右侧的数组是正确函数的结果还是结果数组,因此,通过包含第一个时间,你确保FL\ 的正确参数始终是一个结果数组,而不是一个会被前面添加的元素破坏的裸结果。

\n\n

值得注意的是,您也可以以二元方式调用这样的链,在这种情况下,其所有函数(不是FL)都将使用相同的两个参数以二元方式调用。例如,X(f FL g FL\xe2\x88\x98\xe2\x8a\x82h)Y与以下相同(X f Y)(X g Y)(X h Y)。但是,您可能希望以单子方式调用某些函数。虽然与当前的问题没有直接关系,但这个一元运算符将使函数忽略其左参数(如果有),并且对此目的非常有帮助,因为您避免了括号:

\n\n
M \xe2\x86\x90 {\xe2\x8d\xba\xe2\x8d\xba \xe2\x8d\xb5}\n
Run Code Online (Sandbox Code Playgroud)\n\n

因此,假设我们有四个函数fghp,并且我们希望以一元方式调用g和,同时保留和 的p左侧参数。现在我们已经实现了,我们可以通过作为左参数和作为右参数来做到这一点:fhMXY

\n\n
X(f FL g M FL h FL\xe2\x88\x98\xe2\x8a\x82p M)Y\n
Run Code Online (Sandbox Code Playgroud)\n\n

我再次建议,如果您决定实现此一元运算符,则应将其名称长度保持在 1 个字符以内。

\n