Re: Unmanaged mode in RefPtr



2014-11-21 15:02 GMT+01:00 Kjell Ahlstedt <kjell ahlstedt bredband net>:
Have you tried:
Glib::RefPtr<Query> query = QueryAllocation::create();
do_sth(query);
Glib::RefPtr<QueryAllocation> alloc_query = Glib::RefPtr<QueryAllocation>::cast_dynamic(query);
It's not very nice, but if it works, it's better than fiddling with unreference() and reference().
It doesn't really solve my problem, but it's still some kind of workaround (probably better than my trick with inc/dec refcounts, but still - workaround). When I'd like to call QueryAllocation's methods, I have to do castings:
       
           Glib::RefPtr<QueryAllocation>::cast_static(query)->call1();
          Glib::RefPtr<QueryAllocation>::cast_static(query)->call2();
It's inconvenient.
The obvious suggestion is to fix do_sth(). It's really odd to require refcount==1.
It's not odd in gstreamer. A lot of methods requires refcount equals 1, because if refcount is greater, a copy of object is created (or even assertion fails, in some cases). That's why I don't want to increase refcount, if it's in fact not necessary. Of course, I can implement my method as template function:

          template<typename T> void do_sth(const Glib::RefPtr<T>& arg);

and it's even type-safe, but I've got bad feelings about it. It's tricky, type of argument isn't obvious, and a lot of code has to be moved to a header files (or instantiate template by every possible query type in source file, but it's inconvenient).

Best regards,
Marcin Kolny


Kjell

Den 2014-11-21 10:18, Marcin Kolny skrev:
Hi,
I've got following problem;                                               
I've got a class Query, which is base class for QueryAllocation. Passing \
QueryAllocation object as Query to a function is pretty simple because of automatic cas\
ting:

void do_sth(const RefPtr<Query>& query);                                  
...
RefPtr<QueryAllocation> alloc_query = QueryAllocation::create ();         
do_sth (alloc_query);                                                     

But... in do_sth method, refcount of my object equals 2 (because casting \
increases ref count, it's obvious). Unfortunately, I have to have refcoun\
t=1 in do_sth method, so that's what I'm doing now:

RefPtr<QueryAllocation> alloc_query = QueryAllocation::create();          
RefPtr<Query> query = alloc_query;                                        
query->unreference();                                                     
do_sth(query);                                                            
query->reference();                                                       
query.reset();                                                            

It's workaround.. that would be great, if I can do something like "unmana\
ged RefPtr". It might look like this:

RefPtr<QueryAllocation> alloc_query = QueryAllocation::create();          
do_sth(RefPtr<Query>(alloc_query, false));                                

And constructor declaration:
template<typename T>
RefPtr(const RefPtr<T>& src, bool manage = true);                         

If 'manage' equals false, RefPtr doesn't increase/decrease refcount durin\
g construction and destruction. I know, it's unsafe, and might lead to a \
problems, if somebody uses it wrong, but it allows me to remove a lot of \
magic from my code.

Of course, it's only conceptual solution, maybe it would be better to do \
single function instead of constructor, ideas are welcome.

Best regards,
Marcin Kolny



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]