In any large scale system, especially one driven by a variety of commands and resources, heap allocations (via
delete) can become serious performance bottlenecks as well as liabilities in memory management due to their unbounded execution time and fragmentation. One effective way to mitigate these issues is to replace your raw allocations with factories that pool your resources for you. You can potentially avoid hundreds of allocations when creating timeline commands, playlists, voices, by only calling new when your pool of inactive objects is empty.
The nice thing about this approach is that it can become almost formulaic, with only situational tweaks when you need to be properly reset and reconfigure recycled resources. As an example, here is a header for a Play Command factory:
As per the comments, the Create method of the factory replaces any raw new you would use for getting Play commands; same for Return and delete. Since audio commands in particular are rampant in this audio engine, this approach is essential; there could easily be dozens of commands for each instance of a playlist, multiplied by many sound calls on the game thread.
Resource pooling via factories is a very effective way to minimize the footprint caused by a large amount of small allocations and allows you to elegantly request resources without manually pooling memory by hand. Next up in this series (Part 3) is a discussion about designing a central timeline for your engine.