Forums > Dev

getting all object that belong to one class

April 24, 2007 | 9:00 pm

Hi there,

I have an external called ‘foo’.
20 instances of ‘foo’ have been created in a Max patch.
10 instances are in the main patch, the remaining 10 are in subpatchers
at various depths.

Now, I need all 20 instances of ‘foo’ to output certain information in
response to a message that may be received in just ONE instance of any
‘foo’ object.

So, I am guessing I need a way to traverse all object instantiated that
belong to the class ‘foo’.

I did check the SDK of course, but I could not find anything related to
this.

If someone could post an example or point me to some information about
it, I would appreciate it.

Thank you.

- Luigi

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


April 24, 2007 | 9:06 pm

One way that doesn’t involve any patcher traversal: maintain a global
linked list of all instances of foo and iterate through it, sending
each object the message.

You could do it with patcher traversal, but it would be much more
complicated.

jb

Am 24.04.2007 um 23:00 schrieb Luigi Castelli:

> Hi there,
>
> I have an external called ‘foo’.
> 20 instances of ‘foo’ have been created in a Max patch.
> 10 instances are in the main patch, the remaining 10 are in
> subpatchers
> at various depths.
>
> Now, I need all 20 instances of ‘foo’ to output certain information in
> response to a message that may be received in just ONE instance of any
> ‘foo’ object.
>
> So, I am guessing I need a way to traverse all object instantiated
> that
> belong to the class ‘foo’.
>
> I did check the SDK of course, but I could not find anything
> related to
> this.
>
> If someone could post an example or point me to some information about
> it, I would appreciate it.
>
> Thank you.
>
> – Luigi
>
>
> ————————————————————
> THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT
> AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY
> UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS
> PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE
> SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF
> THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
> ————————————————————
>
>
> Do You Yahoo!?
> Tired of spam? Yahoo! Mail has the best spam protection around
> http://mail.yahoo.com


April 24, 2007 | 9:26 pm

On 07-04-24, at 1400, Luigi Castelli wrote:
> Hi there,
>
> I have an external called ‘foo’.
> 20 instances of ‘foo’ have been created in a Max patch.
> 10 instances are in the main patch, the remaining 10 are in
> subpatchers
> at various depths.
>
> Now, I need all 20 instances of ‘foo’ to output certain information in
> response to a message that may be received in just ONE instance of any
> ‘foo’ object.
>
> So, I am guessing I need a way to traverse all object instantiated
> that
> belong to the class ‘foo’.
>
> I did check the SDK of course, but I could not find anything
> related to
> this.
>
> If someone could post an example or point me to some information about
> it, I would appreciate it.
>
I can’t post a whole example, but the following method works for me:

create a boxed object (foo)
in the foo new routine, find or create a boxless object (foohelper)
keep a pointer to foohelper in foo
keep a linked list of boxed objects in foohelper
each time you create or delete a foo, update the linked list in
foohelper, and delete foohelper when all the foos are deleted (i.e.
reference counting)
keep global state in foohelper, and pass messages through as needed.

This may be overly complicated for your needs, depending on the state
that needs to be shared. In my case, I’m sharing a single network
socket across a bunch of objects, so it has to live in its own
object. You may be able to get away with a single global linked list
that you manage in the foo new/free methods if you don’t require that
much sharing between your objects.

here is some code to find/create a hidden object:

t_symbol *hidden = gensym("foohidden");

if (hidden != _sym_nothing && hidden->s_thing) {
if (ob_messlist(hidden->s_thing) != foo_hidden_class->c_messlist) {
error("name in use", 0);
return NULL;
} else {
xx = (t_foo_hidden *)hidden->s_thing;
}
} else {
xx = foo_hidden_new(hidden);
hidden->s_thing = (t_object *)xx;
}

Essentially this looks up an object by name in the global max symbol
table. If it doesn’t exist, it creates a new one and associates it
with that symbol.

If you need more code snips or explanations, let me know.

r.


April 25, 2007 | 5:59 am

Thank you Jeremy and Ritchie,

I implemented your suggestion and it works like a charm.
I don’t need too much sharing between my objects so the simple global
linked list solution is what I went for.

Now I find myself iterating through the linked list a lot, so I was
wondering if – for the sake of efficiency – there is any difference
between these two constructs:

for (p = head; p; p = p->next) {
// do something
}

and

p = head;
while (p) {
p = p->next;
}

…or is there any reason why I should want one over the other ?

Thanks guys.

- Luigi

— Ritchie Argue wrote:

> On 07-04-24, at 1400, Luigi Castelli wrote:
> > Hi there,
> >
> > I have an external called ‘foo’.
> > 20 instances of ‘foo’ have been created in a Max patch.
> > 10 instances are in the main patch, the remaining 10 are in
> > subpatchers
> > at various depths.
> >
> > Now, I need all 20 instances of ‘foo’ to output certain information
> in
> > response to a message that may be received in just ONE instance of
> any
> > ‘foo’ object.
> >
> > So, I am guessing I need a way to traverse all object instantiated
>
> > that
> > belong to the class ‘foo’.
> >
> > I did check the SDK of course, but I could not find anything
> > related to
> > this.
> >
> > If someone could post an example or point me to some information
> about
> > it, I would appreciate it.
> >
> I can’t post a whole example, but the following method works for me:
>
> create a boxed object (foo)
> in the foo new routine, find or create a boxless object (foohelper)
> keep a pointer to foohelper in foo
> keep a linked list of boxed objects in foohelper
> each time you create or delete a foo, update the linked list in
> foohelper, and delete foohelper when all the foos are deleted (i.e.
> reference counting)
> keep global state in foohelper, and pass messages through as needed.
>
> This may be overly complicated for your needs, depending on the state
>
> that needs to be shared. In my case, I’m sharing a single network
> socket across a bunch of objects, so it has to live in its own
> object. You may be able to get away with a single global linked list
>
> that you manage in the foo new/free methods if you don’t require that
>
> much sharing between your objects.
>
> here is some code to find/create a hidden object:
>
> t_symbol *hidden = gensym("foohidden");
>
> if (hidden != _sym_nothing && hidden->s_thing) {
> if (ob_messlist(hidden->s_thing) != foo_hidden_class->c_messlist) {
> error("name in use", 0);
> return NULL;
> } else {
> xx = (t_foo_hidden *)hidden->s_thing;
> }
> } else {
> xx = foo_hidden_new(hidden);
> hidden->s_thing = (t_object *)xx;
> }
>
> Essentially this looks up an object by name in the global max symbol
>
> table. If it doesn’t exist, it creates a new one and associates it
> with that symbol.
>
> If you need more code snips or explanations, let me know.
>
> r.
>

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


April 25, 2007 | 6:25 am

On 07-04-24, at 2259, Luigi Castelli wrote:
> Thank you Jeremy and Ritchie,
>
> I implemented your suggestion and it works like a charm.
> I don’t need too much sharing between my objects so the simple global
> linked list solution is what I went for.
>
> Now I find myself iterating through the linked list a lot, so I was
> wondering if – for the sake of efficiency – there is any difference
> between these two constructs:
>
I would recommend (a) worrying about readability over efficiency, and
to that end (b) looking at ext_linklist.h, and not do any of the low-
level linklist stuff yourself.

r.


April 25, 2007 | 11:42 am

On Apr 24, 2007, at 11:25 PM, Ritchie Argue wrote:

> I would recommend (a) worrying about readability over efficiency,
> and to that end (b) looking at ext_linklist.h, and not do any of
> the low-level linklist stuff yourself.

Not to mention thread safety. If your linked list may be modified in
both the low priority and high priority threads, you’ll need to use
some kind of thread safe locks (see ext_systhread.h and online
documentation about threads and locks like the following sample
chapters from Modern Operating Systems: http://www.cs.vu.nl/~ast/
books/mos2/samples.html

The linklist calls take care of this for you. However, while they
will work in a DSP perform method, you may not want to use these
functions internal to a DSP perform method for performance reasons,
in which case you might want to use some lighter weight means of
achieving synchronization than OS supplied mutexes.

Though, as *always*, optimize last, and even then use profiling tools
and focus on code which is the bottle neck. Worrying about whether a
while loop or a for loop is more efficient is typically the least
efficient use of your mind. On OS X, Apple’s Shark is a great
profiling tool.

-Joshua


April 25, 2007 | 9:36 pm

Quote: Luigi Castelli wrote on Wed, 25 April 2007 07:59
—————————————————-
> for (p = head; p; p = p->next) {
> // do something
> }
>
> and
>
> p = head;
> while (p) {
> p = p->next;
> }
>
> …or is there any reason why I should want one over the other ?

—————————————————-

According to the C-spec the two are identical. Two different ways of generating the same machine code. There is certainly no difference in efficiency.

Either construct can be made thread-safe.

The for-loop has a certain atomicity in its syntax that some people may prefer.


April 26, 2007 | 12:51 am

Hi guys,

first of all, thanks Peter for your explanation.

It seems from what Joshua and Ritchie are saying that I am better off
using the ext_linklist.h API to manage my linked list. That way I don’t
have to worry about thread safety, and don’t have to come up with my
own linked list functions. Makes sense…

Now, the reason why I didn’t go with the ext_linklist.h API yet, is
because I am not sure if it provides the low level functionality I
need. To be more specific, in my code I am acually managing two linked
lists.

In various parts of the code I need to perform the following action:

for (a = a_head; a; a = a->next) {
for (b = b_head; b; b = b->next) {
// do something
}
}

Is nesting two linked list like that something possible with the
ext_linklist.h API ?
Or am I now better off implementing my own linked list functions and
deal with all the thread issues of the case ?

Thanks.

- Luigi

— Peter Castine

wrote:

>
> Quote: Luigi Castelli wrote on Wed, 25 April 2007 07:59
> —————————————————-
> > for (p = head; p; p = p->next) {
> > // do something
> > }
> >
> > and
> >
> > p = head;
> > while (p) {
> > p = p->next;
> > }
> >
> > …or is there any reason why I should want one over the other ?
>
> —————————————————-
>
> According to the C-spec the two are identical. Two different ways of
> generating the same machine code. There is certainly no difference in
> efficiency.
>
> Either construct can be made thread-safe.
>
> The for-loop has a certain atomicity in its syntax that some people
> may prefer.
> –
> ————– http://www.bek.no/~pcastine/Litter/
> ————-
> Peter Castine +–> Litter Power & Litter Bundle for
> Jitter
>
> iCE: Sequencing, Recording & Interface Building for Max/MSP
> Extremely cool http://www.dspaudio.com/
>
>

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


April 26, 2007 | 2:02 am

On Apr 25, 2007, at 5:51 PM, Luigi Castelli wrote:

> Is nesting two linked list like that something possible with the
> ext_linklist.h API ?
> Or am I now better off implementing my own linked list functions and
> deal with all the thread issues of the case ?

Do you mean a list of lists? Sure. the nodes of the list can be any
object (or a pointer or integer masquerading as an object):

t_linklist *mainlist = linklist_new();
t_linklist *sublist = linklist_new();
linklist_append(mainlist,(t_object *)sublist);

You might find the methodall or funall routines useful for iteration.
If you have a specific question, feel free to post it with relevant
code.

-Joshua


April 26, 2007 | 2:39 am

Thanks Joshua,

will do…

Just for my own curiosity, does the ext_linklist API implement singly
linked or doubly linked lists under the hood ?

- Luigi

— Joshua Kit Clayton wrote:

>
> On Apr 25, 2007, at 5:51 PM, Luigi Castelli wrote:
>
> > Is nesting two linked list like that something possible with the
> > ext_linklist.h API ?
> > Or am I now better off implementing my own linked list functions
> and
> > deal with all the thread issues of the case ?
>
> Do you mean a list of lists? Sure. the nodes of the list can be any
> object (or a pointer or integer masquerading as an object):
>
> t_linklist *mainlist = linklist_new();
> t_linklist *sublist = linklist_new();
> linklist_append(mainlist,(t_object *)sublist);
>
> You might find the methodall or funall routines useful for iteration.
>
> If you have a specific question, feel free to post it with relevant
> code.
>
> -Joshua
>

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


April 26, 2007 | 10:31 am

Joshua,

upon more careful reading of your answer I am not entirely sure I can
do what I want.
I don’t really mean a list of lists, but a way of nesting iterations
of linked lists.

here is a more specific example:

how would you do the following with the ext_linklist.h API ?

void myfunction (void)
{
t_myobject *obj = NULL;
t_mydevice *dev = NULL;
t_atom a[1];

obj = myobject_list_head; // point to head of list 1
while (obj) {
outlet_anything(obj->out, _sym_clear, 0, 0L);
dev = mydevice_list_head; // point to head of list 2
while (dev) {
atom_setsym(a, gensym(dev->name));
outlet_anything(obj->out, _sym_append, 1, a);
dev = dev->next;
}
obj = obj->next;
}
}

If you can confirm to me that the above if possible with the
ext_linklist.h API I will be happy to use it. Otherwise I am gonna have
to find another solution.

Thanks again.

- Luigi

— Joshua Kit Clayton wrote:

>
> On Apr 25, 2007, at 5:51 PM, Luigi Castelli wrote:
>
> > Is nesting two linked list like that something possible with the
> > ext_linklist.h API ?
> > Or am I now better off implementing my own linked list functions
> and
> > deal with all the thread issues of the case ?
>
> Do you mean a list of lists? Sure. the nodes of the list can be any
> object (or a pointer or integer masquerading as an object):
>
> t_linklist *mainlist = linklist_new();
> t_linklist *sublist = linklist_new();
> linklist_append(mainlist,(t_object *)sublist);
>
> You might find the methodall or funall routines useful for iteration.
>
> If you have a specific question, feel free to post it with relevant
> code.
>
> -Joshua
>

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


April 26, 2007 | 11:17 am

um, why not do it the same way?

t_linklist *objlist;
t_linklist *devlist;

// assuming that you’ve put some stuff in these lists

long objsize, devsize;
long i, j;

objsize = linklist_getsize(objlist);
devsize = linklist_devsize(devlist);

for (i = 0; i < objsize; i++) {
t_myobject *obj = linklist_getindex(objlist, i);
for (j = 0; j < devsize; j++) {
t_mydevice *dev = linklist_getindex(devlist, i);

atom_setsym(a, gensym(dev->name));
outlet_anything(obj->out, _sym_append, 1, a);
}
}

This is just email-client code, not tested. You should but some error
checking in, and ensure that you’re using the t_linklists properly,
but this is exactly what you’ve done.

If you are putting your own objects (which you want to free yourself)
into the linked lists, don’t forget to use linklist_chuck(), instead
of freeobject(mylinkedlist). linklist_chuck() frees the list without
freeing the objects contained in it. freeobject() will free both the
list, and all objects contained by it.

jb

Am 26.04.2007 um 12:31 schrieb Luigi Castelli:

> Joshua,
>
> upon more careful reading of your answer I am not entirely sure I can
> do what I want.
> I don’t really mean a list of lists, but a way of nesting iterations
> of linked lists.
>
> here is a more specific example:
>
> how would you do the following with the ext_linklist.h API ?
>
> void myfunction (void)
> {
> t_myobject *obj = NULL;
> t_mydevice *dev = NULL;
> t_atom a[1];
>
> obj = myobject_list_head; // point to head of list 1
> while (obj) {
> outlet_anything(obj->out, _sym_clear, 0, 0L);
> dev = mydevice_list_head; // point to head of list 2
> while (dev) {
> atom_setsym(a, gensym(dev->name));
> outlet_anything(obj->out, _sym_append, 1, a);
> dev = dev->next;
> }
> obj = obj->next;
> }
> }
>
> If you can confirm to me that the above if possible with the
> ext_linklist.h API I will be happy to use it. Otherwise I am gonna
> have
> to find another solution.
>
> Thanks again.
>
> – Luigi
>
>
>
>
>
>
> — Joshua Kit Clayton wrote:
>
>>
>> On Apr 25, 2007, at 5:51 PM, Luigi Castelli wrote:
>>
>>> Is nesting two linked list like that something possible with the
>>> ext_linklist.h API ?
>>> Or am I now better off implementing my own linked list functions
>> and
>>> deal with all the thread issues of the case ?
>>
>> Do you mean a list of lists? Sure. the nodes of the list can be any
>> object (or a pointer or integer masquerading as an object):
>>
>> t_linklist *mainlist = linklist_new();
>> t_linklist *sublist = linklist_new();
>> linklist_append(mainlist,(t_object *)sublist);
>>
>> You might find the methodall or funall routines useful for iteration.
>>
>> If you have a specific question, feel free to post it with relevant
>> code.
>>
>> -Joshua
>>
>
>
>
> ————————————————————
> THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT
> AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY
> UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS
> PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE
> SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF
> THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
> ————————————————————
>
>
> Do You Yahoo!?
> Tired of spam? Yahoo! Mail has the best spam protection around
> http://mail.yahoo.com


April 26, 2007 | 5:44 pm

of course….

thanks Jeremy and sorry for the silly question. I wasn’t thinking…

Now – as far as thread safety goes – when I am traversing lists like in
my (your) example, I don’t need to use any locking mechanism such as
critical regions or systhread calls, do I ?

I understand everything regarding thread safety is already taken care
for you by the ext_linklist API. Am I correct in making this assumption
?

- Luigi

— Jeremy Bernstein wrote:

> um, why not do it the same way?
>
> t_linklist *objlist;
> t_linklist *devlist;
>
> // assuming that you’ve put some stuff in these lists
>
> long objsize, devsize;
> long i, j;
>
> objsize = linklist_getsize(objlist);
> devsize = linklist_devsize(devlist);
>
> for (i = 0; i < objsize; i++) {
> t_myobject *obj = linklist_getindex(objlist, i);
> for (j = 0; j < devsize; j++) {
> t_mydevice *dev = linklist_getindex(devlist, i);
>
> atom_setsym(a, gensym(dev->name));
> outlet_anything(obj->out, _sym_append, 1, a);
> }
> }
>
> This is just email-client code, not tested. You should but some error
>
> checking in, and ensure that you’re using the t_linklists properly,
> but this is exactly what you’ve done.
>
> If you are putting your own objects (which you want to free yourself)
>
> into the linked lists, don’t forget to use linklist_chuck(), instead
>
> of freeobject(mylinkedlist). linklist_chuck() frees the list without
>
> freeing the objects contained in it. freeobject() will free both the
>
> list, and all objects contained by it.
>
> jb
>
> Am 26.04.2007 um 12:31 schrieb Luigi Castelli:
>
> > Joshua,
> >
> > upon more careful reading of your answer I am not entirely sure I
> can
> > do what I want.
> > I don’t really mean a list of lists, but a way of nesting
> iterations
> > of linked lists.
> >
> > here is a more specific example:
> >
> > how would you do the following with the ext_linklist.h API ?
> >
> > void myfunction (void)
> > {
> > t_myobject *obj = NULL;
> > t_mydevice *dev = NULL;
> > t_atom a[1];
> >
> > obj = myobject_list_head; // point to head of list 1
> > while (obj) {
> > outlet_anything(obj->out, _sym_clear, 0, 0L);
> > dev = mydevice_list_head; // point to head of list 2
> > while (dev) {
> > atom_setsym(a, gensym(dev->name));
> > outlet_anything(obj->out, _sym_append, 1, a);
> > dev = dev->next;
> > }
> > obj = obj->next;
> > }
> > }
> >
> > If you can confirm to me that the above if possible with the
> > ext_linklist.h API I will be happy to use it. Otherwise I am gonna
>
> > have
> > to find another solution.
> >
> > Thanks again.
> >
> > – Luigi
> >
> >
> >
> >
> >
> >
> > — Joshua Kit Clayton wrote:
> >
> >>
> >> On Apr 25, 2007, at 5:51 PM, Luigi Castelli wrote:
> >>
> >>> Is nesting two linked list like that something possible with the
> >>> ext_linklist.h API ?
> >>> Or am I now better off implementing my own linked list functions
> >> and
> >>> deal with all the thread issues of the case ?
> >>
> >> Do you mean a list of lists? Sure. the nodes of the list can be
> any
> >> object (or a pointer or integer masquerading as an object):
> >>
> >> t_linklist *mainlist = linklist_new();
> >> t_linklist *sublist = linklist_new();
> >> linklist_append(mainlist,(t_object *)sublist);
> >>
> >> You might find the methodall or funall routines useful for
> iteration.
> >>
> >> If you have a specific question, feel free to post it with
> relevant
> >> code.
> >>
> >> -Joshua
> >>
> >
> >
> >
> > ————————————————————
> > THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT
> > AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY
> > UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS
> > PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE
> > SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF
>
> > THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
> > ————————————————————
> >
> >
> > Do You Yahoo!?
> > Tired of spam? Yahoo! Mail has the best spam protection around
> > http://mail.yahoo.com
>
>

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


April 26, 2007 | 5:52 pm

Correct.

jb

Am 26.04.2007 um 19:44 schrieb Luigi Castelli:

> of course….
>
> thanks Jeremy and sorry for the silly question. I wasn’t thinking…
>
> Now – as far as thread safety goes – when I am traversing lists
> like in
> my (your) example, I don’t need to use any locking mechanism such as
> critical regions or systhread calls, do I ?
>
> I understand everything regarding thread safety is already taken care
> for you by the ext_linklist API. Am I correct in making this
> assumption
> ?
>
> – Luigi


April 26, 2007 | 8:02 pm

On Apr 26, 2007, at 10:44 AM, Luigi Castelli wrote:

> Now – as far as thread safety goes – when I am traversing lists
> like in
> my (your) example, I don’t need to use any locking mechanism such as
> critical regions or systhread calls, do I ?

I might regret this as it could serve to confuse the discussion
rather than clarify, but let me actually qualify Jeremy’s "correct"
statement. There will be no linked list corruption, as these calls
are threadsafe with respect to modifying the *data structure*.
However, there *may* be some need for using some thread locking
mechanism like mutexes if you need to have a compound logical
operation complete without modification to the data structures being
used.

For example if you wanted to remove an item off of the tail of the
list and put it at the head of the list, this is a compound logical
operation made up of an element removal and insertion. While the
removal and insertion are *each* threadsafe w/r/t the datastructure
manipulation, there are situations where you would want to make sure
this operation were completed before some other thread did something
like sort the list, or free all members, or whatever. In these types
of scenarios, you will need to implement whatever thread safety you
need to protect the compound logical operation as a complete and
uninterruptible "transaction".

If you want to learn more about this sort of thing, I’ll put another
plug for Tanenbaum’s "Modern Operating Systems", and suggest you
perform some searches on terms like "thread safety compound
transaction".

-Joshua


April 27, 2007 | 8:47 am

Hi Joshua,

thanks for the clarification. It makes perfect sense.

All the actions I am performing with the linked list are:

- create a list
- add a node to the list
- delete a node from the list
- traverse the list
- delete whole list

So, I don’t think I am performing any compound logical operation. The
only actions that actually modify the list is adding a node or deleting
a node, and – of course – disposing of the whole list. However I don’t
think these actions would fall under the compound operation category.
Please correct me if I am wrong here…

Could you please post a simple example of the ext_linklist API usage ?

Let’s say I have a struct declared as following:

typedef struct _node {
long *ptr;
long a;
long b;
long c;
} t_node;

How would I create a list, append and remove nodes ?
How would I traverse it ? How would I dispose the whole list ?

I am also not sure what the t_llelem struct is for.
And finally what’s the difference between linklist_append and
linklist_appendnode ?

I think I am generally not clear about how I would go to use it.

Thank you.

- Luigi

— Joshua Kit Clayton wrote:

>
> On Apr 26, 2007, at 10:44 AM, Luigi Castelli wrote:
>
> > Now – as far as thread safety goes – when I am traversing lists
> > like in
> > my (your) example, I don’t need to use any locking mechanism such
> as
> > critical regions or systhread calls, do I ?
>
> I might regret this as it could serve to confuse the discussion
> rather than clarify, but let me actually qualify Jeremy’s "correct"
> statement. There will be no linked list corruption, as these calls
> are threadsafe with respect to modifying the *data structure*.
> However, there *may* be some need for using some thread locking
> mechanism like mutexes if you need to have a compound logical
> operation complete without modification to the data structures being
>
> used.
>
> For example if you wanted to remove an item off of the tail of the
> list and put it at the head of the list, this is a compound logical
> operation made up of an element removal and insertion. While the
> removal and insertion are *each* threadsafe w/r/t the datastructure
> manipulation, there are situations where you would want to make sure
>
> this operation were completed before some other thread did something
>
> like sort the list, or free all members, or whatever. In these types
>
> of scenarios, you will need to implement whatever thread safety you
> need to protect the compound logical operation as a complete and
> uninterruptible "transaction".
>
> If you want to learn more about this sort of thing, I’ll put another
>
> plug for Tanenbaum’s "Modern Operating Systems", and suggest you
> perform some searches on terms like "thread safety compound
> transaction".
>
> -Joshua
>

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


May 1, 2007 | 12:09 am

Hi guys,

I would appreciate if someone could post a few usage examples of the
ext_linklist.h API.

I would love to see something basic like how to create a new list, add
nodes, remove nodes, traverse list and delete list.
Also, I am a little confused about the t_llelem type and difference
between linklist_appendnode and linklist_append or between linklist_new
and linklistelem_new…

Thanks for any clarification.

- Luigi

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


May 1, 2007 | 2:32 am

On Apr 30, 2007, at 5:09 PM, Luigi Castelli wrote:

> I would appreciate if someone could post a few usage examples of the
> ext_linklist.h API.
>
> I would love to see something basic like how to create a new list, add
> nodes, remove nodes, traverse list and delete list.

Not a lot of time for this sort of thing, but here’s the basics from
an email client (might be a few typos). The only real thing you need
to pay attention to is if you’re using objects (created with
object_new()) or structs. If the latter you need to be responsible
for freeing the structs yourself and using "chuck" calls to remove
from list without calling freeobject().

// make a list
t_linklist *list = linklist_new();

// add an object (or struct) to a list
linklist_append(list,(t_object *)myobject);

// remove object at index 0 from the list, freeing the object with
freeobject() internally (not appropriate for structs)
linklist_delete(list,0);

// remove object or struct at index 0 from the list, without freeing
the object or struct
linklist_chuckindex(list,0);

// retrieve an object or struct at index 0
myobject = (t_myobject *) linklist_getindex(list,0);

// call a method on all objects in list (not appropriate for structs)
linklist_methodall(list,gensym("foo"));

// call a function on all objects in list
linklist_functionall(list,(method)myfunction,(void *)mydata);

//free a list, freeing all objects (not appropriate for structs)
linklist_free(list);

//free a list, without freeing all objects or structs
linklist_chuck(list);

> Also, I am a little confused about the t_llelem type and difference
> between linklist_appendnode and linklist_append or between
> linklist_new
> and linklistelem_new…

You can safely ignore t_llelem and all "node" related calls which are
for internal use only.

-Joshua


May 1, 2007 | 7:26 am

Hi there,

does anybody know if it’s faster to compare strings with strings or
symbols with symbols ?

Example:

——————-
char myString1[16];
char myString2[16];

myString1 = "maxmspjitter"
myString2 = "maxmspjitter"

if (strcmp(myString1, myString2) == 0) {
// do something
}
——————-

or

——————-
t_symbol *mySymbol1;
t_symbol *myStmbol2;

mySymbol1 = gensym("maxmspjitter");
mySymbol2 = gensym("maxmspjitter");

if (mySymbol1 == mySymbol2) {
// do something
}
——————-

Thank you.

- Luigi

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


May 1, 2007 | 7:55 am

Hi Luigi,
comparing symbols is faster, as it’s just comparing two pointers
(which are simply integer numbers).
strcmp involves comparing the bytes the string pointers point two,
and some more logic too.

all the best,
Thomas

Am 01.05.2007 um 09:26 schrieb Luigi Castelli:

> Hi there,
>
> does anybody know if it’s faster to compare strings with strings or
> symbols with symbols ?
>
> Example:
>
> ——————-
> char myString1[16];
> char myString2[16];
>
> myString1 = "maxmspjitter"
> myString2 = "maxmspjitter"
>
> if (strcmp(myString1, myString2) == 0) {
> // do something
> }
> ——————-
>
> or
>
> ——————-
> t_symbol *mySymbol1;
> t_symbol *myStmbol2;
>
> mySymbol1 = gensym("maxmspjitter");
> mySymbol2 = gensym("maxmspjitter");
>
> if (mySymbol1 == mySymbol2) {
> // do something
> }
> ——————-
>
> Thank you.
>
> – Luigi
>
>
> ————————————————————
> THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT
> AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY
> UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS
> PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE
> SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF
> THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
> ————————————————————
>
>
> Do You Yahoo!?
> Tired of spam? Yahoo! Mail has the best spam protection around
> http://mail.yahoo.com
>

Thomas Grill

http://grrrr.org


May 1, 2007 | 7:58 am

sorry, i forgot….
what i wrote is only true if the gensym in your code is not taken
into account.
If your symbols are constant (have a known string content) you could
cache them beforehand e.g. by storing the symbol pointer in a static
variable.

greetings,
Thomas

Am 01.05.2007 um 09:26 schrieb Luigi Castelli:

> Hi there,
>
> does anybody know if it’s faster to compare strings with strings or
> symbols with symbols ?
>
> Example:
>
> ——————-
> char myString1[16];
> char myString2[16];
>
> myString1 = "maxmspjitter"
> myString2 = "maxmspjitter"
>
> if (strcmp(myString1, myString2) == 0) {
> // do something
> }
> ——————-
>
> or
>
> ——————-
> t_symbol *mySymbol1;
> t_symbol *myStmbol2;
>
> mySymbol1 = gensym("maxmspjitter");
> mySymbol2 = gensym("maxmspjitter");
>
> if (mySymbol1 == mySymbol2) {
> // do something
> }
> ——————-
>
> Thank you.
>
> – Luigi
>
>
> ————————————————————
> THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT
> AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY
> UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS
> PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE
> SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF
> THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
> ————————————————————
>
>
> Do You Yahoo!?
> Tired of spam? Yahoo! Mail has the best spam protection around
> http://mail.yahoo.com
>

Thomas Grill

http://grrrr.org


May 1, 2007 | 5:44 pm

I think my thought process as to the trade off is: am I going to re-
use the strings? If you think that you’ll have a bunch of the same
strings coming in, or you’ll be comparing a bunch of inputs to a small
number of cached strings, then by all means gensyms and use the string-
table goodness built into max. If not, then you’ll be wasting a bunch
of space, as the gensym function probably keeps the strings around for
the duration of the max process.

_Mark

On May 1, 2007, at 12:58 AM, Thomas Grill wrote:

> sorry, i forgot….
> what i wrote is only true if the gensym in your code is not taken
> into account.
> If your symbols are constant (have a known string content) you could
> cache them beforehand e.g. by storing the symbol pointer in a static
> variable.
>
> greetings,
> Thomas
>
> Am 01.05.2007 um 09:26 schrieb Luigi Castelli:
>
>> Hi there,
>>
>> does anybody know if it’s faster to compare strings with strings or
>> symbols with symbols ?
>>
>> Example:
>>
>> ——————-
>> char myString1[16];
>> char myString2[16];
>>
>> myString1 = "maxmspjitter"
>> myString2 = "maxmspjitter"
>>
>> if (strcmp(myString1, myString2) == 0) {
>> // do something
>> }
>> ——————-
>>
>> or
>>
>> ——————-
>> t_symbol *mySymbol1;
>> t_symbol *myStmbol2;
>>
>> mySymbol1 = gensym("maxmspjitter");
>> mySymbol2 = gensym("maxmspjitter");
>>
>> if (mySymbol1 == mySymbol2) {
>> // do something
>> }
>> ——————-
>>
>> Thank you.
>>
>> – Luigi
>>
>>
>> ————————————————————
>> THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT
>> AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY
>> UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS
>> PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE
>> SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF
>> THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
>> ————————————————————
>>
>>
>> Do You Yahoo!?
>> Tired of spam? Yahoo! Mail has the best spam protection around
>> http://mail.yahoo.com
>>
>
> Thomas Grill
> http://grrrr.org
>
>


May 1, 2007 | 6:10 pm

On 1 May 2007, at 08:26, Luigi Castelli wrote:

> t_symbol *mySymbol1;
> t_symbol *myStmbol2;
>
> mySymbol1 = gensym("maxmspjitter");
> mySymbol2 = gensym("maxmspjitter");

In this case, you’re not testing the comparison of symbol pointers
(which should be very fast), but the speed of the hash function. I
would certainly expect the hash to be slower than strcmp(), but that
won’t matter if the gensym() calls have been done already (such as by
Max itself).

– N.

Nick Rothwell / Cassiel.com Limited
http://www.cassiel.com
http://www.myspace.com/cassieldotcom
http://www.loadbang.net


May 1, 2007 | 6:36 pm

Mark, Nick, Thomas,

thanks for your replies guys…

I am dealing with 4 pairs of strings. (8 strings in total)
Each pair is made of two matching strings. (i.e. they are the same)

I am calling gensym on all 4 pairs of strings at object creation time.
(myobject_new method)
After that I am not touching the strings or symbols any more.

During runtime I need a function to compare every string/symbol with
the other eight to find the matching pair. Some kind of 4×4 symbol
matrix, basically.

That’s why I was wondering about speed and efficiency since the
comparisons end up being many.

It seems to understand from your posts that in this case the fastest
way is to compare symbols – or symbol pointers to be more precise -
instead of strings.

Thanks for your help.

- Luigi

— Nick Rothwell wrote:

>
> On 1 May 2007, at 08:26, Luigi Castelli wrote:
>
> > t_symbol *mySymbol1;
> > t_symbol *myStmbol2;
> >
> > mySymbol1 = gensym("maxmspjitter");
> > mySymbol2 = gensym("maxmspjitter");
>
> In this case, you’re not testing the comparison of symbol pointers
> (which should be very fast), but the speed of the hash function. I
> would certainly expect the hash to be slower than strcmp(), but that
>
> won’t matter if the gensym() calls have been done already (such as by
>
> Max itself).
>
> – N.
>
>
> Nick Rothwell / Cassiel.com Limited
> http://www.cassiel.com
> http://www.myspace.com/cassieldotcom
> http://www.loadbang.net
>
>
>
>

————————————————————
THIS E-MAIL MESSAGE IS FOR THE SOLE USE OF THE INTENDED RECIPIENT AND MAY CONTAIN CONFIDENTIAL AND/OR PRIVILEGED INFORMATION. ANY UNAUTHORIZED REVIEW, USE, DISCLOSURE OR DISTRIBUTION IS PROHIBITED. IF YOU ARE NOT THE INTENDED RECIPIENT, CONTACT THE SENDER BY E-MAIL AT SUPERBIGIO@YAHOO.COM AND DESTROY ALL COPIES OF THE ORIGINAL MESSAGE. WITHOUT PREJUDICE UCC1-207.
————————————————————

Do You Yahoo!?
Tired of spam? Yahoo! Mail has the best spam protection around

http://mail.yahoo.com


Viewing 24 posts - 1 through 24 (of 24 total)