You know, a fun misconception I've seen a lot lately is that lists are automatically better than vectors when you want to do a lot of pushes and pops, or insertions at random points.
This often proves wrong because of the wonders of CPU-level caching. Always profile before going away from vector, except when you need iterators that will remain valid so long as the item they point to isn't removed and are therefore forced to use list. It turns out
the frequent CPU cache misses are too expensive when you iterate over lists for them to stack up well against vectors in many situations where you'd think lists should be best.
Don't blame the tool if you don't use it right.
I wasn't blaming the tool, I was pointing out mistakes that result in "undefined behaviour" are the riskiest part of C++ programming, and where at best a lot of cross-platform compatibility is halted, and at worst a lot of difficult-to-track-down crashes come from.
Whilst often the same behaviour in a JIT'd language will cause a crash, but they often do things to get around that such as being explicitly specified to throw an exception with an occasionally helpful error message. You simply have to be aware how C++, not being JIT'd and being a lot more leaned towards power without restraints, doesn't give you that luxury.
For example, an iterator to a vector can in theory be invalidated as soon as that vector is modified (push or pop). It'll bite you in the arse eventually, so just never store iterators to a vector for a period in which a vector is mutable. If you do, then C#/Java would throw a somewhat readable exception here, whilst a program written in C++ will experience a seemingly random crash at best.
This kind of thing is why C++ fills the niche it does, and they are both the languages greatest strength and greatest weakness.