Sometimes pure data is really doing my head in and feels so counterintuitive
At the leftt there are three message boxes "-" "kick" and "hat " ..in Pure data world these are are (implicit)symbols.
The select module however does not identify these because there is NO symbol selector , this feels so counter intuitive .
When sending a list through a list store and retrieve the individual elements , a symbol selector is automatically added since the select module accepts these
-
Symbols explicit
-
@whale-av said:
Try things out with pd-selector.pd
Hi, you seem to have created some sort of abstraction that makes [route] match to list messages, huh?
Well, if that's the case, let me tell you all about [else/route2], which is also part of PlugData. I guess it can do all the things that people would expect [route] to do and this is why I wrote it.
I guess it's not clear from the description it can route to the first element of a list message, I will improve that description now.
-
@whale-av said:
Try things out with pd-selector.pd
hey, I see you're using [route] and [select] with many messages and trying to explain the results. What example do you have here that is not included in the help file? Also, I see you're sending a list message to [select] and to me it implies that it some how understands and deals with list message, which is not true, and is not documented either.
What happens there is what happens to any pd object when you send it a list and it doesn't expect a list method, it splits the list and distributes it to its inlets. So what you're doing is rewriting/replacing the argument in the right inlet.
This is why if you try to send 11 23 into [select me] you will get the error "inlet: expected 'symbol' but got 'float'"
-
@porres I cannot remember to tell the truth as it was a long time ago. Yes, I believe what started my "investigation" (learning session) was finding that a list could be distributed across the inlets....which surprised me for this object.
Maybe that could be described as a bug, as I cannot see that anyone would ever have used it for any purpose, and it can cause problems.
David. -
@gentleclockdivider When you need to turn a list into a message remember that the only difference between them is the list has a list selector so [list prepend set] -> [list trim] will do the same and save you from endlessly having to add and remove dollar arguments from your [set $1 $2 $3...( messages as your list length changes, and it also works with listbox since it also has the set method.
If you are dealing with lists, uses list objects even if you are trying to turn that list into a message, it will make life easier and often you find you don't even need the message, the list objects will handle it all. Despite being able to click on them messages are not actually UI objects, hence their not showing up in GOPs, they are for constructing those internal messages which lack selectors like all those methods for [list store] and why they produce an error if you click on one with a dollar argument in it and needing a list or symbol selector in them when you want to use them for a list or a symbol. -
@whale-av said:
Maybe that could be described as a bug, as I cannot see that anyone would ever have used it for any purpose
I'd bet that the following theorem is true:
All Turing-complete languages contain useless statements
-
@whale-av said:
Maybe that could be described as a bug, as I cannot see that anyone would ever have used it for any purpose, and it can cause problems
well, just to add to the discussion, this is not a bug at all. It is a feature of Pd that is meaningless for this object, and it is also meaningless or very silly to other objects. It's just that disabling this feature for this object would be quite work, as you'd need to create a special handling of a list method.
This feature just bypasses the need of the [unpack] object. If you wanted to have a list unpacked and then distributed to both inlets of [sel], that wouldn't be a bug, just something not really meaningful or useful. There are many silly and meaningless things you could do in a Pd patch, it doesn't mean it's a bug or something.
-
FWIW, as someone who is no stranger to programming concepts, I have to say that I've gotten tripped up on datatype selectors more than once. They are "basic" but I wouldn't say intuitive.
With that said, I sometimes joke that Pd shows us where Miller Puckette learned from Max's mistakes. E.g., Max's [poly~] is... hoo boy... the hacks. The. Hacks. ... where [clone] is (relatively) clean, direct, minimal. Or [/ 2] is integer division by default in Max (nobody wants this). Or the fact that Pd's timing model includes sub-audio-block timing.
Still, inconsistencies remain.
One might reasonably expect at least [symbol abc] to pass through both [select abc] and [route abc] -- but [select] requires the symbol tag, and [route] rejects it. Of course there is some principle in there somewhere, but I maintain, that's pretty weird: two objects that perform matching, that require differently-formatted input.
hjh
-
[route] only matches to the 1st element, and passes the rest of the message. It would more properly need to handle lists... in the case of a symbol, it's kinda pointless to send it to route, as you can only have a bang output, and this is not the purpose of that object. It is the point of the [select] object though.
I don't think this is an issue for [route] at all. Having said that, [route] has many issues. It has inconsistencies (like how it doesn't trim the symbol selector). I don't debate about its bad design. That's why I wrote [route2]
and I also have [routetype] and [routeall]... in [route2] it can manage a list message and route the rest.
This is not about the language concept and design, it's about the object design. I see design problems in many object, but hey, help file is there to show how the object works one way or another, even if it has inconsistencies.
-
@porres said:
[route] only matches to the 1st element, and passes the rest of the message. It would more properly need to handle lists... in the case of a symbol, it's kinda pointless to send it to route, as you can only have a bang output, and this is not the purpose of that object. It is the point of the [select] object though.
I'm thinking of the Ruby "principle of least surprise," by which a behavior of an object or function may be justifiable, but suboptimal because it can easily trip users up.
Which is nicer for users? They both just work the way you'd think (match it, and it passes through), or to enforce subtle distinctions and thereby get in the user's way? (Not saying here that it's always a good thing to let sloppy thinking slide, but, neither is it always good to rub the user's nose in design decisions.)
Symbols aren't "the point" of [route], but why then does [route] not automatically strip the "list" tag? Least surprise would be to just do the thing the user wanted instead of blowing a raspberry, "nya nya, you forgot [list trim] again"
(and cheers for route2 on that front).
hjh
-
@ddw_music said:
Symbols aren't "the point" of [route], but why then does [route] not automatically strip the "list" tag?
What do you mean? It does strip it... sending "list dog cat" to [route] strips (or "trims") the list selector and outputs "dog cat". Or do you mean, why doesn't it have a list method and understands that you have a list and then must route according to the first element?
Well, as to why it is as it is, I just looked at the code. I had a guess that it was just overlooked, so, a bug, a mistake. But I see now there was a clear intent to trim the list selector, and, I don't know why, it doesn't make much sense to me, I have to agree. It seems it wanted to to data type routing, as it can do [route float], and also pointer, but then it just failed with the list data type.
So as I see there were some bad design choices/mistakes, but Pd is very conservative and careful on this sense, and some real and clear bugs are documented as is, check [bendin]/[bendout].
As someone who designs lots of objects, I can see how even if we try hard, we always tend to find some mistakes and regret some choices. This is why ELSE has been on "experimental" mode for almost a decade. I just fix and change the behaviour and design, but this opposite extreme is also bad
and I will finally stop doing that when PlugData 1.0 is out, which might happen this year
and then I'll just have to live with some screw ups.
But hey, I think that ELSE fixes and deals fine with routing elements like [route], or data types, or the whole message with [routeall]
-
@ddw_music said:
but why then does [route] not automatically strip the "list" tag?
Lists were simpler things in the early days of pd with [pack] being the primary list object, there was no [list], so an object just to trim the selector would seem somewhat useless with how lists could be used and [route] doing the trim would be sensible. Quick look and [list] did not get added to pd until 0.39. Possibly a lack of foresight/planing or possibly things evolved differently than planned.
@oid That was a useless post. Good use of lists unpacking to inlets.
Can make much neater patches than [list store] and really gets you to structure your data and patch right to left which often results in a messy patch with [list store]. Interestingly both [i ] and [f ] show this behavior, which really seems useless but more than once I have found an error in a patch because of this and one of those errors which would have been difficult to spot otherwise. -
@oid said:
Lists were simpler things in the early days of pd with [pack] being the primary list object, there was no [list], so an object just to trim the selector would seem somewhat useless with how lists could be used and [route] doing the trim would be sensible. Quick look and [list] did not get added to pd until 0.39. Possibly a lack of foresight/planing or possibly things evolved differently than planned.
hmmm, I see, and yeah, I get that a lot with my library, which keeps growing and growing. And a lot of bad decisions I face is when I add more objects, or different objects, or want to add new features...
If I never added objects it would be much more stable and I wouldn't break things so much. It's hard to know before hand what you will want to do in the future
anyway, that makes sense indeed, thanks
-
I've read the updated manual back and forth but there are still some things unclear to me .
Take the following example
The message c3 f3 a3 , the first selector is c3 and thus this message is an implicit symbol , correct ?It's not a list because the list gatom does not understand it ., neither does the symbol gatom , so is it an unindentified message ?
Putting the same message through a list and the listbox understands it ( since the message starts with a symbol atom, a list must be explicitly given )
Next , the message c3,f3,a3 , three messages after each other each with a symbol identifier
Putting these through a list and we get again 3 successive messages each with a symbol identifier , the symbol gatom only understands it after list processing ( obviously only one element is shown since the message is separated )
-
@gentleclockdivider said:
The message c3 f3 a3 , the first selector is c3 and thus this message is an implicit symbol , correct ?
No, it is just a message, to be a symbol it would need the symbol selector. We have three selectors; float, symbol and list, when an object gets a message it checks for those selectors to make sure it is getting the correct type of data, if it lacks one of those selectors it treats it as a method like 'set' so your [list store] knows it should set its internal state instead of operate on the data and produce output. The alternative would be to have reserved words which you would have to escape or add a selector to, so if you wanted a [list] to store the message [set 1 2 3( you would have to do [list set 1 2 3( or [\set 1 2 3(. The pd way avoids reserved words which means we don't have memorize a long list of reserved words, just the three selectors and the mostly consistent ways they are handled.
Next , the message c3,f3,a3 , three messages after each other each with a symbol identifier
None of those have a symbol selector, those are just three messages. You can run those through a [symbol] instead of a [list] and for this sort of thing that is a good idea, explicitly states that it is a symbol so you don't have to trace the patch to figure out what is going on.
-
@oid said:
@gentleclockdivider said:
The message c3 f3 a3 , the first selector is c3 and thus this message is an implicit symbol , correct ?
No, it is just a message, to be a symbol it would need the symbol selector. We have three selectors; float, symbol and list, when an object gets a message it checks for those selectors to make sure it is getting the correct type of data, if it lacks one of those selectors it treats it as a method like 'set' so your [list store] knows it should set its internal state instead of operate on the data and produce output. The alternative would be to have reserved words which you would have to escape or add a selector to, so if you wanted a [list] to store the message [set 1 2 3( you would have to do [list set 1 2 3( or [\set 1 2 3(. The pd way avoids reserved words which means we don't have memorize a long list of reserved words, just the three selectors and the mostly consistent ways they are handled.
Next , the message c3,f3,a3 , three messages after each other each with a symbol identifier
None of those have a symbol selector, those are just three messages. You can run those through a [symbol] instead of a [list] and for this sort of thing that is a good idea, explicitly states that it is a symbol so you don't have to trace the patch to figure out what is going on.
But the manual clearly states that the first atom in a message is the selector , and for mesage c3 d3 e3 , the first atom is c3 .
Isn't c3 a symbol , it starts with the letter C ?
When the message is separated by commas , and send though a list , the console clearly shows these are seperate symbols , why then ?
To be fair , I think pure data is a million times more complex than supercollider or anything else I have worked withManual :
quoteMessages contain a selector followed by any number of arguments. The selector is a symbol that defines the message type. The arguments are anything that follows and may be symbols or numbers (aka atoms). For instance "list a b c" has a "list" selector, which defines the "list" data type, and "a b c" is the actual message. This message is only composed of symbols but a list message can combine two or more symbols and/or floats.
unquote
-
@gentleclockdivider I think that excerpt from the manual kind of gets overly technical, depends on how earlier parts of the manual handle things. Technically, everything in your patch is either a float or a symbol but selectors tell objects how they should treat it and if the object does not see a selector it recognizes it prints an error to the console. Selectors are not types, more like methods and I sort of used "selector" as type and made methods separate. The symbol selector has one argument, a symbol and each object treats the first item in a message as the selector to tell it how to deal with its arguments.
Perhaps @porres or another dev will chime in on selectors vs methods in pd, both are used in the help files, are they interchangeable? Should they be unified or distinguished better? That excerpt muddles the distinction, if there is one.
When the message is separated by commas , and send though a list , the console clearly shows these are seperate symbols , why then ?
Because those are three separate messages each being sent to [list] in order from left to right, [list] is one of the objects with no methods and applies the appropriate selector to the data it receives. Try that with an object which has methods like [list store], won't work, you will get three errors.
To be fair , I think pure data is a million times more complex than supercollider or anything else I have worked with
for years I had that same feeling about pd, spending some time in vanilla pd with no externals helped a good deal, got me over the hurdle with understanding the quirks of pd and dataflow.
-
@gentleclockdivider said:
The message c3 f3 a3 , the first selector is c3 and thus this message is an implicit symbol , correct ?
nope, there are no implicit symbols in Pd. Symbols are defines with the "symbol" selector, and can take only one argument, quote from the manual "The symbol selector can only have one symbol argument"
It's not a list because the list gatom does not understand it ., neither does the symbol gatom , so is it an unindentified message ?
nope, it is a defined message, with a defined selector
@oid said:
We have three selectors; float, symbol and list
No. that's wrong, we have "infinite" selectors. The selector is a symbol that defines the data type (as the manual says). So, any symbol that comes first in a message is the selector. There some special selectors alright, but they are not just three, but five! Another quote from the manual: These special types are: "float", "symbol", "list", "bang" and "pointer"
if it lacks one of those selectors it treats it as a method like 'set' so your [list store]
The "set" IS the selector. What you refer as a "method" is if the object understands that message selector. So it means it has a function (or "method") to deal with it. If it does not, it will say "no method for set", but it can also say "no method for symbol/float/bang", so it's the same for the special selectors as is with any other general selector. (I see you asked me to chime in later about this, well, here it is).
@gentleclockdivider said:
But the manual clearly states that the first atom in a message
is the selector , and for mesage c3 d3 e3 , the first atom is c3 .
Isn't c3 a symbol , it starts with the letter C ?Yes, it is a symbol, hence, it is the selector of the message, so "c3 d3 e3" is a message whose selector is "c3" and the actual message is "d3 e3".
When the message is separated by commas , and send though a list ,
the console clearly shows these are seperate symbols , why then ?they are separated because you're using commas, and commas separate the atoms. And if you sent it to print, you wouldn't see the symbol selector. But since you're passing them through [list] they are gaining a list selector. But since lists need to have two or more elements, one-length lists are converted to a symbol or float message (I think we discussed this on this thread already, and the help file of [list] discusses that).
Now, to be honest, I don't understand why you brought this up here, and why do you ask. I don't see the relation. Just let it be clear that you have 3 messages with just a symbol, and that these are selectors! What is the message then? No message, just selectors. The manual exemplifies something like this when it says about the "stop" message, let me quote it: "If a message contains only one symbol, like "stop", it is considered a selector with no actual message (i.e., no arguments) attached."
I guess the manual could have more examples of generic selectors maybe? I don't know what is exactly not clear in the manual, please let me know so I can see if I can improve it.
@oid said:
I think that excerpt from the manual kind of gets overly technical
Why do you say that?
it's telling it as it is...
-
I guess this subpatch that I referenced to earlier has more examples and makes things clearer? Should I bring some of this into the manual?
Anyway, thanks for checking the docs and letting me know if they can be improved
-
I think pure data is a million times more complex than supercollider
Oh, don't get me started with SuperCollider
geez, that thing is what I call a nightmare
Thee whole syntax of Pd is so damn simple, I can teach it quickly in a single class. The syntax of SuperCollider, on the other hand... damn,... what a PITA
There are really a couple of tricky things to learn about Pd's syntax, like the dollar sign deal, and how to deal with selectors, and that's it. And the deal is that the first thing (symbol) in a message sets the message type (feels simple, clear and straightforward to me), and you have some special data types. I really cannot see the complexity in here! I guess it becomes simple once it's all clear to you.
And I hope it is clear now
cheers