std::vector operator [] is evil?

Started by
24 comments, last by werekarg 18 years, 9 months ago
Hello all I've made an interesting discovery while optimizing the performance of my 3D game app. Using operator [] to index STL vectors in performance-critical loops seems to seriously hurt framerate. Multiple nested index operators worsen it even more, eg:
something = verts[tris.vindex[j]];
where verts and tris are STL vectors. Has anyone else experienced this? When I switched to either using iterators in loops or just convetional C arrays in place of std::vectors, framerate rise from 63 FPS to whopping 122 FPS. [rolleyes] I'm using Visual Studio.NET 2002 and Dinkumware STL implementation bundled with it.
Advertisement
I'm not always someone who defends the STL, but I'd say the the implementation of the STL you are using probably does play some factor in there. Plus there is going to be some small loss of performance just do to the bounds checking that the vector class does (which does make it safer to use than your typical c/c++ style array).

"I can't believe I'm defending logic to a turing machine." - Kent Woolworth [Other Space]

All the STL implementations I've come across do not do bounds-checking on std::vector::operator[] by default.

Arkion, good performance for std::vector depends on the compiler correctly inlining function calls. Are you compiling in Debug mode? If so, then you shouldn't trust ANYTHING about speed differences. Only draw conclusions based on Release mode builds, with full optimization.
Operator[] usually doesn't bounds check; I believe a function called at() does. I don't know the actual name, because it has been a while since I used C++ and its STL.
It is the diet-coke of evil.
I wrote quick program to see the difference between vector and array access and the only difference of note were these two lines. Other than these two lines, the generated assembly was the same for both.
00401247  mov         esi,dword ptr [v+4 (411490h)] 0040124D  add         edi,offset a (409380h) 

Using a vector requires one additional indirection.

Here is my source:
static vector< s >	v( size );static s		a[ size ];	for ( int i = 0; i < size; ++i )	{		int j = rand();		int k = rand();		a[j] = v[k];	}


I can't see how changing from vector to array would double your frame rate, unless there is something really unique about your code. Along with Sneftel, I suspect you are profiling your debug configuration. It's a common mistake.
John BoltonLocomotive Games (THQ)Current Project: Destroy All Humans (Wii). IN STORES NOW!
If you're using MS VisualStudio then remember it's also affected by what mode you're running. A friend profiled std::string and std::vector and the results are much faster in Release mode. Debug mode has a load of extra faff for debugging information and error checking.

/Edit: misread post - argh. Duly corrected.
__________________________________Peter Lewis ([email=me_AT_pjblewis.com]E-mail[/email] | Portfolio)
Don't profile in debug mode.

If you arn't, update your compiler to something developed this millenia.
The STL in a release compile is fast. I mean faster than anything I've recreated.

My homebrew array class' in debug compile are way faster than VECTOR.
In release mode VECTOR wins, it unrolls a lot into asm I believe which is more than any hobbiest wants to do.

I can send you performance tests and a array class.
I had a similar problem to this using maps. I may be wrong on this but I think:

When you use the [] operator the element in the vector gets copied. So if you have a vector of vectors, the inner vector will get copied when you use the first [] operator. This would account for the performance hit, and certainly did with my map of maps.

Like I say I could be wrong but I seem to remember reading somewhere that this is the case.
"Absorb what is useful, reject what is useless, and add what is specifically your own." - Lee Jun Fan

This topic is closed to new replies.

Advertisement