最近,我阅读了很多关于SuperCollider的教程和论坛,并且在使用*、#和_的一些代码示例中遇到了麻烦,但我不知道为什么要使用它们?有人能给我解释一下吗?这与避免多通道扩展有关吗?
一些样本:
(
var list = [1, 2, 3];
func(*list); // equivalent to func(list[0], list[1], list[2])
)或
var a, b, c;
#a, b, c = [1, 2, 3]; // equivalent to a=1; b=2; c=3;或
p = Pbind(
\degree, Pwhite(-7, 12, inf),
\dur, Pwrand([0.25, Pn(0.125, 2)], #[0.8, 0.2], inf),
\legato, Pfunc { ~legato } // retrieves value set by MIDI control
).play;
)或者(在Pseq中)
(
Pbind(
\mtranspose, -1,
\octave, 5,
[\dur, \degree], Ptuple(y.collect(Pseq(_, inf)))
).play
)发布于 2021-01-06 14:26:32
阿斯特里克斯
您的示例快速展示了这一工作方式的总结,但让我们对其进行一些扩展,并定义一个三个参数函数:
f = { arg a, b, c;
a + b + c;
};当我们想要调用函数时,我们可以执行:f.value(1,1,1),它返回3。
现在,由于某种原因,我们有一个由三个数字组成的数组,我们希望将它们传递给函数。
a = [1, 1, 1];如果我们只是尝试f.value(a),我们只是一个错误。我们可以通过指定f.value(a[0], a[1], a[2])来解决这个问题,也可以使用*快捷方式。这会将数组分解为传递给函数的列表。因此,等效的、较短的语法是f.value(*a)。
庞德
磅/散列符号(无论你怎么称呼它)可以分为两种不同的东西,取决于它的去向。让我们从一个数组开始:
a = [1, 2, 3];假设您有三个变量,并希望它们获得数组内容。你可以这样做:
b = a[0];
c = a[1];
d = a[2];但这需要大量的输入,所以一个等价的快捷方式是
#b, c, d = a#的另一个含义是,当它出现在数组的开始括号之前时。尼克·柯林斯说:
--关于效率的一点注记
你偶尔会看到
#[1,2,3] //makes a totally fixed (non-dynamic) Array and is slightly cheaper, especially where you're not going to change the Array once you make it而不是
[1,2,3] //a dynamic array 以显示差异
a= #[1,2,3];
a[0] //works
a[0] = 8 //fails, because it can't be changed(来自https://composerprogrammer.com/teaching/supercollider/sctutorial/Technicalities/02%20Arrays.html )
下划线
下划线正在执行名为“部分应用程序”的操作。它有一个帮助文件:https://doc.sccode.org/Reference/Partial-Application.html
它正在做的是替换一个参数声明和用法。所以在他们的一个例子中,你可以写:
(1..10).collect({ arg n; n.squared });或者你可以稍微缩短一下:
(1..10).collect( _.squared );因此,_正在接管声明和使用n。注意,_还意味着您不使用{}括号。在示例代码中,可以将Ptuple(y.collect(Pseq(_, inf)))重写为Ptuple(y.collect({arg z; Pseq(z, inf)}))。
语法快捷方式
所有这些快捷方式统称为“句法糖”。有一个名为“SuperCollider”的帮助文件,但是如果您只是在学习,我建议您暂时避免使用它,只在遇到一个符号做一些奇怪的事情时才使用它。
https://stackoverflow.com/questions/64988991
复制相似问题