I've been reading through a lot of tutorials and forums on SuperCollider lately, and came accross on some code samples using *
and #
and _
, but I don't find why they are used ? Can someone explain that to me ? Is this related to avoiding multichannel expansion ?
Some samples:
(
var list = [1, 2, 3];
func(*list); // equivalent to func(list[0], list[1], list[2])
)
or
var a, b, c;
#a, b, c = [1, 2, 3]; // equivalent to a=1; b=2; c=3;
or
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;
)
or (in the Pseq
)
(
Pbind(
\mtranspose, -1,
\octave, 5,
[\dur, \degree], Ptuple(y.collect(Pseq(_, inf)))
).play
)
Asterix
Your sample quickly shows a summary of how this works, but let's expand it a bit and define a three argument function:
When we want to call the function, we could do:
f.value(1,1,1)
, which returns 3.Now say for some reason we have an array of three numbers and we want to pass them to the function.
If we just try
f.value(a)
we just an error. We could work around this by specifyingf.value(a[0], a[1], a[2])
or we can use the * shortcut. This breaks up the array into a list for passing to a function. So the equivalent, shorter syntax isf.value(*a)
Pound
The pound/hash sign (whichever you call it) can to two different things, depending where it goes. Let's start with an array:
Let's say you have three variables and you want them to get the array contents. You could do:
But that's a lot of typing, so an equivalent shortcut is
The other meaning of # is when it comes right before the opening bracket of an array. According to Nick Collins:
You will occasionally see
rather than
To show the difference
(from https://composerprogrammer.com/teaching/supercollider/sctutorial/Technicalities/02%20Arrays.html )
Underscore
The underscore is doing something called Partial Application. It has a helpfile: https://doc.sccode.org/Reference/Partial-Application.html
What it's doing is replacing an argument declaration and usage. So in one of their examples, you could write:
Or you could shorten it slightly:
So the _ is taking over declaring and using n. Note that the _ also means that you don't use the
{}
brackets. In your example code,Ptuple(y.collect(Pseq(_, inf)))
could be rewritten asPtuple(y.collect({arg z; Pseq(z, inf)}))
Syntax Shortcuts
All of these shortcuts collectively are called "Syntactic Sugar". There's a helpfile called that, but if you're just learning SuperCollider, I suggest you avoid it for now and only dip in hen you come across a symbol doing something strange.