[Qt-interest] thread safety of Qt containers

Mihail Naydenov mlists at ymail.com
Mon Apr 26 13:22:58 CEST 2010


----- Original Message ----

> From: Andre Somers <andre at familiesomers.nl>
> To: qt-interest at trolltech.com
> Sent: Mon, April 26, 2010 1:14:56 PM
> Subject: Re: [Qt-interest] thread safety of Qt containers
> 
> Hi,

Thanks for your answers so far.

On 26-4-2010 11:41, Thiago 
> Macieira wrote:

> Em Segunda-feira 26 Abril 2010, às 11:26:17, Andre 
> Somers escreveu:
>    
>> Hi,
>>
>> I 
> was wondering:
>> Qt's documentation states that the methods in QList, 
> QVector and QHash
>> (and maybe QMap, I did not check) are reentrant. 
> That means that they
>> can be used in a thread, as long as the 
> instance that is used is not the
>> same, right?
>>  
>     
> Correct.
>
>    
>> So... 
> how does QtConcurrent work? QtConcurrent::map() and the likes have
>> 
> multiple threads operating on data in the same container. How save 
> is
>> that? The docs say that only the non-in place operations make a 
> copy of
>> the container, so that would mean that multiple threads at 
> the same time
>> can write to a QList? They can't be using a 
> QMutableListIterator though,
>> as only one of those can be savely 
> operating on a list at the same time...
>>      
> 
> There's a mutex. That ensures that there's only one thread accessing the
> 
> container at a time.
>    
So, performing a very simple 
> operation using QtConcurrent is not that 
efficient, because of the locking 
> and unlocking of the mutex? I seem to 
recall that mutexes are relatively 
> expensive resources to aquire, right?

>> I am looking into 
> QtConcurrent to speed up some heavy calculation work
>> that I need to 
> do. However, the amount of data is such that copying
>> around data is 
> really not an option. It is simply too much (datasets may
>> range into 
> the GB range).
>>      
>
Would it be save to 
> read from the same datastructure from multiple 
threads, if not write to 
> them?

André

If you use QtConcurrent you are stuck with QFuture to access the data and let Qt handle writing to it.
This means you cannot avoid locking the mutex on write (Qt) and read (you: QFuture.result ()/ QFuture.resultAt())  [1].

There also other limitations too - like for instance if you use uninitialized (not returned from run() or maped()) QFuture, the status report (running etc) is wrong
This means you can not use  reliably a QFuture as a  class member and initialize it later when needed, test if its started() finished() etc..
Also, QFuture is sotight to QtConcurrent, you cannot event set or clear(!) the data it hold (to free space for instance).  [2]

And of course the this means, QFuture cannot be used outside QTConcurrent, this is, in some threading implementation of yours.


So, for simple concurrent tasks QtConcurrent is great. 
But if you have *any* wishes beyond the basics, you have to implement something from scratch (using QThreadPool is a good start, again to bad, you cant reuse QFuture also)
OR use other solutions like Intels TBB ot whatever. Qt, although it does the job,  has by no means a pro support for concurrent programming.
 
MihailNaydenov

[1]There is also some bug with that locking it seams, see:
http://bugreports.qt.nokia.com/browse/QTBUG-6799
[2]This is my experience from some time ago, things might have changed), Scan the mailist for more info.

_______________________________________________
Qt-interest 
> mailing list

> href="mailto:Qt-interest at trolltech.com">Qt-interest at trolltech.com
http://lists.trolltech.com/mailman/listinfo/qt-interest


      




More information about the Qt-interest-old mailing list