[PD] PD OOP?

brandon zeeb zeeb.brandon at gmail.com
Wed Dec 15 16:50:41 CET 2010


#7: and on and on In most Pd patches, I see people using a few lookup tables
again and again (ie: mtof). As this is a complete waste of memory

Say you compute a raised cosine window and store it in a table, this table
is used within one instance of a granular table reading voice abstraction,
1-n of these abstractions are created at run time for polyphony.  Now you
have N instances of this table.  Some people cache mtof in a table, and thus
that was my original point.

2. No control over abstraction (object) construction order and lifecycle

In a given abstraction you do NOT have control of the order in which your
abstractions are created in memory.  With my attempt at the Flyweight
pattern for large lookup tables, it became apparent that if I were to remove
an abstraction while editing a patch, I would have no idea if I removed the
abstraction with reference to the real table or not.  This is almost similar
to prototypal inheritance where the instantiated object controls the
resource, not the prototype.  For example, a given UI on an Android phone
widget will usually share graphic resources with others of it's type to save
memory.

IMHO, directing your criticism at pd-vanilla alone is extremely
unproductive. You have to accept the fact that doing real work in Pd may
require a lot of externals. It's sad, but it's like that. I wouldn't use Pd
if it didn't have externals.

I care more about Pd as a language and as a means to learn. For my purposes,
using externals is pointless, although I do appreciate all the hard work.

#5. No interfaces or abstract abstractions (to control inlet patterns)

I would like to know which inlets of a given abstraction are signals and
which are events for the purpose of dynamic patching / autowiring.  Bonus
points if inlet metadata is available.

With a bit of introspection, one could determine the name of the inlet, and
thus autowire (dynamically patch) it to the correct binding (binding in my
library, u_dispatch in RjDj).  I work around this by enforcing a strict
interface (as with RjDj) of two event inlets (hot and cold) where the cold
inlet receives binding (dispatch) events.  ~ objects just prepend signal
inlets to the hot-side.

Please first give an example of a useful use of the FlyweightPattern.

Any given abstraction that requires a large lookup table obtains a reference
(ie: the table name) of this large table without having to construct it by
itself, it doesn't know how to create it, it just receives it... but every
abstraction that requires this table receives the same one.  This is much
like a singleton.  Otherwise it's a complete waste of resources.

 6. Unfriendly and inconsistent type system (it is cumbersome in real use,
> although I get over this by using [list])
>

I once proposed alternate versions of [unpack], [select], etc., that had no
type restrictions. There was a discussion on it. See :

That would be great.  In my uses I don't really need a [unpack a a a],
usually by the time I reach a [pack] I already have a strong enough
determination of what types I'm working with (my binding/dispatch is
type-agnostic though), but it would be nice.

Is this just ONE kind of InversionOfControl (IoC) ? I'd guess that there are
several quite different manners of doing that in Pd, no ? But I have trouble
reading definitions and tutorials of IoC. I probably have used a bunch of
different IoC techniques in Pd and other languages already.

Basically, an abstraction (or object) is given what it needs to function by
a 3rd party.  The abstraction in question only focuses on it's given task
and doesn't know how to create it's dependencies.  For testability and
reusability, this is a fantastic pattern.  So far I've been using
constructor IoC (in creation arguments), but one could just as easily pass
this information as a list to an abstraction's inlet.  Max's [poly] and
RjDj's u_makepoly~ objects are a very simple example of this.

If you look at the structure of any given synthesizer voice in Pd, I'm sure
you can think of other useful examples of this.

Cheers,
~Brandon


On Wed, Dec 15, 2010 at 10:23 AM, Mathieu Bouchard <matju at artengine.ca>wrote:

> On Wed, 15 Dec 2010, brandon zeeb wrote:
>
>   2. No control over abstraction (object) construction order and lifecycle
>>
>
> What's that ?
>
>   3. No introspection (although not required, very helpful, and don't tell
>> me it's in some external, I don't care!)
>>
>
> Why do you don't care about externals that might do the job ???
>
> IMHO, directing your criticism at pd-vanilla alone is extremely
> unproductive. You have to accept the fact that doing real work in Pd may
> require a lot of externals. It's sad, but it's like that. I wouldn't use Pd
> if it didn't have externals.
>
>   5. No interfaces or abstract abstractions (to control inlet patterns)
>>
>
> Strictly speaking, interfaces, or completely abstract classes, need only be
> made explicit in languages that have strict method-lookup. In languages like
> Python/Ruby/Perl/Tcl/ObjC/etc., all the lookup is at run time, and likewise
> for PureData. In those languages, there is usually no built-in way to
> declare interfaces, because the method-lookup wouldn't use those
> declarations anyway.
>
> Strict method-lookup normally means that "anything-methods" don't exist,
> and that means that complicated workarounds have to be provided instead of
> solutions that depend on "anything-methods" and loose method-lookup.
>
> I would like to know what you mean by "inlet patterns" here.
>
>   6. Unfriendly and inconsistent type system (it is cumbersome in real use,
>> although I get over this by using [list])
>>
>
> I once proposed alternate versions of [unpack], [select], etc., that had no
> type restrictions. There was a discussion on it. See :
>
>  http://www.mail-archive.com/pd-list@iem.at/msg08636.html
>  http://www.mail-archive.com/pd-list@iem.at/msg08644.html
>  but also the rest of the thread...
>
>  7. and on and on In most Pd patches, I see people using a few lookup
>> tables again and again (ie: mtof). As this is a complete waste of memory,
>>
>
> [mtof] does not use a lookup-table :
>
>  t_float mtof(t_float f) {
>    if (f <= -1500) return 0;
>    if (f > 1499) return mtof(1499);
>    return 8.17579891564 * exp(.0577622650 * f);
>  }
>  void mtof_float(t_object *x, t_float f) {
>    outlet_float(x->ob_outlet, mtof(f));
>
>  }
>
>  one can attempt the Flyweight pattern.
>>
>
> Please first give an example of a useful use of the FlyweightPattern.
>
>
>  [bypass~ some_process~ 330 1 3 9]
>>
>
> Is this just ONE kind of InversionOfControl (IoC) ? I'd guess that there
> are several quite different manners of doing that in Pd, no ? But I have
> trouble reading definitions and tutorials of IoC. I probably have used a
> bunch of different IoC techniques in Pd and other languages already.
>
> I mean that even simple patches without any abstractions would use
> implicitly IoC in some manner.
>
>
>  Where [bypass~] expects it's 1st argument to be an abstraction and the
>> next 10 to be arguments to that abstraction.
>>
>
> If you used externals, you could make the number of arguments to be
> variable and unlimited. You could also make it lookup the abstraction in the
> parent's folder, so that I can put some_process~.pd in the same folder as
> the main patch, for example.
>
>
>  Every patch which uses [bypass]~ must have 1 signal inlet and 1 event
>> inlet.  Unfortunately, this interface can't be programmatically enforced.
>>
>
> It's enforced at run time. There's also nothing wrong to having more than 2
> inlets in this case, as long as you wouldn't be using the extra inlets in
> that case anyway (or can do without them).
>
>
>  _______________________________________________________________________
> | Mathieu Bouchard ---- tél: +1.514.383.3801 ---- Villeray, Montréal, QC
>



-- 
Brandon Zeeb
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.puredata.info/pipermail/pd-list/attachments/20101215/586aeca2/attachment.htm>


More information about the Pd-list mailing list