/**
* @file growable_vector.h
* Auto-expanding vector type
*
* @remark Copyright 2002 OProfile authors
* @remark Read the file COPYING
*
* @author John Levon
* @author Philippe Elie
*/
#ifndef GROWABLE_VECTOR_H
#define GROWABLE_VECTOR_H
#include <vector>
#include <algorithm>
#include <functional>
/**
* A simple growable vector template.
*/
template <typename T> class growable_vector {
public:
typedef std::vector<T> container_type;
typedef typename container_type::size_type size_type;
/**
* Index into the vector for a value. An out of
* bounds index will return a default-constructed value.
*/
T operator[](size_type index) const {
if (index >= container.size())
return T();
return container[index];
}
/**
* Index into the vector for a value. If the index is larger than
* the current max index, the array is expanded, default-filling
* any intermediary gaps.
*/
T & operator[](size_type index) {
if (index >= container.size())
container.resize(index + 1);
return container[index];
}
/**
* vectorized += operator
*/
growable_vector<T> & operator+=(growable_vector<T> const & rhs) {
if (rhs.container.size() > container.size())
container.resize(rhs.container.size());
size_type min_size = min(container.size(), rhs.container.size());
for (size_type i = 0 ; i < min_size; ++i)
container[i] += rhs.container[i];
return *this;
}
/**
* vectorized -= operator, overflow shouldn't occur during substraction
* (iow: for each components lhs[i] >= rhs[i]
*/
growable_vector<T> & operator-=(growable_vector<T> const & rhs) {
if (rhs.container.size() > container.size())
container.resize(rhs.container.size());
size_type min_size = min(container.size(), rhs.container.size());
for (size_type i = 0 ; i < min_size; ++i)
container[i] -= rhs.container[i];
return *this;
}
/// return current size of vector
size_type size() const {
return container.size();
}
/// fill container with given value
void fill(size_type size, T const & value) {
container.resize(size, value);
}
/// return true if all elements have the default constructed value
bool zero() const {
return std::find_if(container.begin(), container.end(),
std::bind2nd(std::not_equal_to<T>(), T()))
== container.end();
}
private:
container_type container;
};
#endif // GROWABLE_VECTOR_H