Overloading of new and delete: Object Pool
We have already written an own-defined queue data structure MyQueue before, which maintains a dynamic array as its private member. This time, we are going to rewrite MyQueue, using linked list as its underlying implementation.
Here we use a nested struct QueueItem as the list node, and keep tracking the front and rear of our linked list. Now suppose we are using our new queue in this way:
Here we keep pushing and poping items from the queue for ten thousand times. In our current implementation, each time an element is pushed or popped, a new memory space for QueueItem is allocated and deallocated on the heap. When these operations are very frequent, the memory allocation and deallocation is consuming. To improve this, we can reuse the list nodes we'v already created.
An object pool is a good approach in cases that a large number of objecs are constructed and destroyed in a short time. There are other kinds of pools like thread pool or connection pool, which share the same idea of resource reuse.
The main idea of object pool is to create a pool of objects at once. When an object is created, we get an empty object from the pool. When an object is destroyed, we return it back to the pool. Here we use a static linked list of 10000 QueueItems whose memory space is continuous. A pointer _pool points to the first empty element in the pool. Then we can overload the member function operator new() and operator delete() of QueueItem.
When a new QueueItem is created, we simply return _pool to it, and move _pool to the next empty element. When a QueueItem is deleted, we do not deallocate the memory. Instead, we change its next element into _pool, and move _pool onto it. In this way, the object is returned back to the pool. If the pool is full, another pool is opened up.
Here we haven't implemented the memory deallocation of the object pool, since it's not straightforward here. Using smart pointers is a clever way to do so, which we will introduce in the
Last updated