Manual memory management still has its place in C++, especially in domains where performance, latency, or control over allocation patterns is critical. But as Roy emphasizes, developers should measure before reaching for low-level strategies:
“The first thing you should do is measure. Make sure the allocator or memory pool you already have doesn’t already do the job. If you're spending time on something, it has to pay off.”
He cites high-frequency trading as an example where even small delays can be unacceptable:
“Say you’re working in the finance domain, and you have nanosecond-level constraints because you need to buy and sell very fast—then yes, sometimes you’ll want more control over what’s going on.”
In such cases, allocation must be avoided during critical execution windows. One option is to pre-allocate memory buffers on the stack.
Modern C++ offers fine-grained control through allocator models. Roy contrasts the traditional type-based model with the polymorphic memory resources (PMR) model introduced in C++17:
“Since C++17, we’ve had the PMR (Polymorphic Memory Resource) model... a PMR vector has a member—a pointer to its allocator—instead of having it baked into the type.”
While PMR introduces a layer of indirection via virtual function calls, Roy notes that the overhead is usually negligible:
“Allocation is a costly operation anyway. So the indirection of a virtual function call isn’t much of a cost—it’s already there in the background.”
But when even that cost is too high, the traditional model may be more appropriate:
“If you're in a domain where nanoseconds matter, even that indirection might be too much. In that case, the traditional model... may be a better choice, even if you have to write more code.”
Roy’s guidance is clear: measure first, optimize only when necessary, and understand the trade-offs each model presents.