10 #pragma managed(push, off) 13 #include <condition_variable> 18 #include <condition_variable> 29 template <
typename T,
typename TInitializer,
typename TCleanup = default_cleanup<T>>
34 : m_initializer(initializer), m_initial_chunk_size(initial_chunk_size), m_chunk_size(chunk_size)
36 new_chunk(initial_chunk_size);
41 while (!m_pool.empty())
43 auto front = m_pool.front();
51 assert(is_from_pool(obj));
59 new_chunk(m_chunk_size);
62 auto obj = m_pool.front();
67 bool empty()
const {
return m_pool.empty(); }
72 auto num_chunks = m_chunk_bounds.size();
74 if (m_chunk_bounds.size() > 0 && m_initial_chunk_size > 0)
76 size += m_initial_chunk_size;
80 size += num_chunks * m_chunk_size;
86 for (
auto& bound : m_chunk_bounds)
88 if (obj >= bound.first && obj <= bound.second)
105 m_chunks.push_back(std::unique_ptr<T[]>(
new T[size]));
106 auto& chunk = m_chunks.back();
107 m_chunk_bounds.push_back({&chunk[0], &chunk[size - 1]});
109 for (
size_t i = 0; i < size; i++)
111 memset(&chunk[i], 0,
sizeof(T));
113 m_pool.push(m_initializer(&chunk[i]));
122 size_t m_initial_chunk_size = 0;
123 size_t m_chunk_size = 8;
126 template <
typename T,
typename TAllocator,
typename TDeleter>
133 while (!m_pool.empty())
135 auto& item = m_pool.top();
147 return m_allocator();
150 auto obj = m_pool.top();
155 bool empty()
const {
return m_pool.empty(); }
157 size_t size()
const {
return m_pool.size(); }
165 template <
typename T,
typename TInitializer,
typename TCleanup = default_cleanup<T>>
169 object_pool(
size_t initial_chunk_size, TInitializer initializer = {},
size_t chunk_size = 8)
170 : inner_pool(initial_chunk_size, initializer, chunk_size)
176 std::unique_lock<std::mutex> lock(m_lock);
177 inner_pool.return_object(obj);
182 std::unique_lock<std::mutex> lock(m_lock);
183 return inner_pool.get_object();
186 bool empty()
const {
return inner_pool.empty(); }
188 size_t size()
const {
return inner_pool.size(); }
190 bool is_from_pool(T* obj)
const {
return inner_pool.is_from_pool(obj); }
object_pool(size_t initial_chunk_size, TInitializer initializer={}, size_t chunk_size=8)
no_lock_object_pool< T, TInitializer, TCleanup > inner_pool
TInitializer m_initializer
std::vector< std::unique_ptr< T[]> > m_chunks
void new_chunk(size_t size)
void return_object(T obj)
bool is_from_pool(T *obj) const
void return_object(T *obj)
std::vector< std::pair< T *, T * > > m_chunk_bounds
no_lock_object_pool(size_t initial_chunk_size, TInitializer initializer={}, size_t chunk_size=8)
void return_object(T *obj)
bool is_from_pool(T *obj) const