Chapel 中的元组连接

Tuple Concatenation in Chapel

假设我正在生成元组并且我想在它们出现时连接它们。我该怎么做呢?以下是逐元素加法:

if ts = ("foo", "cat"), t = ("bar", "dog")

ts += t 给出 ts = ("foobar", "catdog"),

但我真正想要的是ts = (("foo","cat"),("bar","dog"))

所以我猜第一个问题是"does Chapel support tuple concatention?",然后是"is there a binary operator/function for it?",然后是"if not, what is a good way to do it?",最后是"make my life easier if you know a better way of living"。

请按顺序回答问题。

非常感谢您的帮助!!

the first question is "does Chapel support tuple concatention?"

我相信这里的答案是 "no",原因如下:(1) Chapel 变量有一个单一的静态类型,在其生命周期内不能改变,(2) 元组的类型被定义为它的元素的静态数量以及每个元素的类型。因此,给定您的变量 ts

ts = ("foo", "cat")

它的类型是 2*string ("a 2-tuple of strings"),这将阻止它存储值 (("foo","cat"),("bar","dog")),因为 类型是 2*(2*string) ("a 2-tuple of 2-tuples of strings")。因此,虽然这两个元组具有相同数量的元素 (2),但它们的元素类型不同("string" 与“字符串的 2 元组”),因此类型不同(不兼容).

"is there a binary operator/function for it?"

由于上述原因,没有。

then "if not, what is a good way to do it?"

我想到了一些事情,但可能有用也可能没有用,具体取决于您的具体情况。与其尝试重新分配 ts,不如创建一个元组中的元组的新元组:

const ts2 = (ts, t);

你甚至可以在例程中递归地执行此操作,但如果元组增长到任何显着长度,这可能最终会导致代码大小膨胀(因为每次调用函数都会生成不同类型的元组以及它的唯一代码)。

根据我在您的问题中看到的内容,我认为您可能想要使用元组列表或元组的一维数组(向量)。这是一个基于列表的方法:

use List;

var listOfTups: list(2*string);

listOfTups.append(("foo", "cat"));
listOfTups.append(("bar", "dog"));

writeln(listOfTups);

这是一种基于数组的方法:

var arrOfTups: [1..0] 2*string;

arrOfTups.push_back(("foo", "cat"));
arrOfTups.push_back(("bar", "dog"));

writeln(arrOfTups);

在这两者中,我会推荐基于数组的方法,因为数组更优先 class 并且在 Chapel 中功能强大(它们享有句法支持、允许数据并行性、支持标量函数和运算符的提升等),而列表只是一个方便的库。

and lastly "make my life easier if you know a better way of living".

如果您不知道,我想提的另一件事是 Chapel 中的 "varargs" 函数有效地将这些参数转换为元组。所以给出:

proc myFunc(x...) {
  writeln(x.type:string);
}

myFunc(("foo", "cat"), ("bar", "dog"));

输出为:

2*2*string