private:
/**
- * Type to enter into the array. First component will be a flag telling
- * whether the vector is used, second the vector itself.
+ * A type that describes this entries of an array that represents
+ * the vectors stored by this object. The first component of the pair
+ * is be a flag telling whether the vector is used, the second
+ * a pointer to the vector itself.
*/
- typedef std::pair<bool, VectorType *> entry_type;
+ typedef std::pair<bool, std::unique_ptr<VectorType> > entry_type;
/**
* The class providing the actual storage for the memory pool.
* Only one of these pools is used for each vector type, thus allocating all
* vectors from the same storage.
*
- * @author Guido Kanschat, 2007
+ * @author Guido Kanschat, 2007, Wolfgang Bangerth 2017.
*/
struct Pool
{
* Standard constructor creating an empty pool
*/
Pool();
+
/**
- * Destructor. Frees memory and warns about memory leaks
+ * Destructor.
*/
~Pool();
+
/**
* Create data vector; does nothing after first initialization
*/
void initialize(const size_type size);
+
/**
* Pointer to the storage object
*/
* output at the end of an object's lifetime.
*/
size_type total_alloc;
+
/**
* Number of vectors currently allocated in this object; used for detecting
* memory leaks.
#include <deal.II/lac/vector_memory.h>
+#include <deal.II/base/std_cxx14/memory.h>
DEAL_II_NAMESPACE_OPEN
GrowingVectorMemory<VectorType>::Pool::~Pool()
{
// Nothing to do if memory was unused.
- if (data == nullptr) return;
-
- // First, delete all remaining
- // vectors. Actually, there should
- // be none, if there is no memory
- // leak
- for (typename std::vector<entry_type>::iterator i=data->begin();
- i != data->end();
- ++i)
- {
- delete i->second;
- }
+ if (data == nullptr)
+ return;
+
+ // delete the 'data' object. this also releases all vectors
+ // that are pointed to by the std::unique_ptrs
+ data->clear();
delete data;
}
++i)
{
i->first = false;
- i->second = new VectorType;
+ i->second = std_cxx14::make_unique<VectorType>();
}
}
}
GrowingVectorMemory<VectorType>::alloc ()
{
Threads::Mutex::ScopedLock lock(mutex);
+
++total_alloc;
++current_alloc;
// see if there is a free vector
if (i->first == false)
{
i->first = true;
- return (i->second);
+ return i->second.get();
}
}
- // no free vector found, so let's
- // just allocate a new one
- const entry_type t (true, new VectorType);
- pool.data->push_back(t);
+ // no free vector found, so let's just allocate a new one
+ pool.data->emplace_back(entry_type (true, std_cxx14::make_unique<VectorType>()));
- return t.second;
+ return pool.data->back().second.get();
}
GrowingVectorMemory<VectorType>::free(const VectorType *const v)
{
Threads::Mutex::ScopedLock lock(mutex);
+
for (typename std::vector<entry_type>::iterator i=pool.data->begin();
i != pool.data->end(); ++i)
{
- if (v == (i->second))
+ if (v == i->second.get())
{
i->first = false;
--current_alloc;
{
Threads::Mutex::ScopedLock lock(mutex);
- std::vector<entry_type> new_data;
-
if (pool.data != nullptr)
- {
- const typename std::vector<entry_type>::const_iterator
- end = pool.data->end();
- for (typename std::vector<entry_type>::const_iterator
- i = pool.data->begin(); i != end ; ++i)
- if (i->first == false)
- delete i->second;
- else
- new_data.push_back (*i);
-
- *pool.data = new_data;
- }
+ pool.data->clear();
}