Click to See Complete Forum and Search --> : std::map iterator


Clash
December 7th, 2008, 04:44 PM
Hello!
I have a multithreaded application that every frame iterates through a map. The problem is, one of the threads might remove one element of the map and the other one could be iterating through the map, this is bad, correct? I could instead of directly removing, just mark the element for elimination and before the loop that iterates through the elements remove those elements. Is this the recommended way, is there another way or am I just doing everything wrong?
If I haven't gave enough information please tell me. Thanks in advance guys.

TheCPUWizard
December 7th, 2008, 04:51 PM
Hello!
I have a multithreaded application that every frame iterates through a map. The problem is, one of the threads might remove one element of the map and the other one could be iterating through the map, this is bad, correct? I could instead of directly removing, just mark the element for elimination and before the loop that iterates through the elements remove those elements. Is this the recommended way, is there another way or am I just doing everything wrong?
If I haven't gave enough information please tell me. Thanks in advance guys.

1) STL is NOT thread safe, YOU must handle this.
2) Modifying a collection may invalidate iterators.

Those two facts should answer your questions.

One solution is to use immutable objects when dealing with multi-threaded applications. This eliminates the need to EVER perform synchronization. The technique does take a boit of getting used to....

Clash
December 7th, 2008, 05:14 PM
By using immutable objects you mean using the const attribute? This would make things quite hard

Lindley
December 7th, 2008, 05:17 PM
You do know what a mutex is, don't you?

Clash
December 7th, 2008, 05:24 PM
Not really, no, and I'm not no Visual Studio if that is something from there

TheCPUWizard
December 7th, 2008, 05:40 PM
By using immutable objects you mean using the const attribute? This would make things quite hard

"Conventional" synchronization (Mutex, Semaphore, Lock, etc) all impose a performance penalty on EVERY access, even when they are there to protect against a "one in a million" chance. Also it is virtually impossible to make sure that your object view is consistant without talking looooong locks.

using imutable (yes that means constant) objects removes this completely, and is the methodology of choice as parallism increases (what happens when your code is running of a 32+ core processor???).

As a psuedo example:

template<T>
class Collection
{
public:
Collection<T> Add(T item) const;
{
Collection<T> retVal(*this);
retVal.InternalAdd(item);
return item;
}
Collection<T> lRemove(T item)
{
Collection<T> retVaxl(*this);
retVal.InternalRemove(item);
return item;
}
private:
Collection<T> InternalAdd(T item)
{
// actuall add the object to this..
}
Collection<T> InternalRemove(T item)
{
// actuall add the object to this..
}

}

Now once a collection is created, it can never be modified. To fill from a list (this would be optimized in real code)

Collection<T> col = new Collection<T>();
foreach (Item item in source)
col = col.Add(item);
return col;

Lindley
December 8th, 2008, 05:05 PM
Not really, no, and I'm not no Visual Studio if that is something from there

Learn. You have to understand mutexes *at the least* before you do anything else with multi-threading. Personally I like pthreads or Boost::thread, since it's cross-platform, but the next revision of the C++ standard will contain standard threading mechanisms including mutexes.