00001
00005 #pragma once
00006
00007 #include <usml/types/seq_vector.h>
00008
00009 namespace usml {
00010 namespace types {
00011
00012 using boost::numeric::ublas::vector;
00013
00016
00027 class USML_DECLSPEC seq_data : public seq_vector {
00028
00029 protected:
00030
00032 size_type _index;
00033
00035 value_type _value;
00036
00038 value_type _index_data;
00039
00041 value_type _sign;
00042
00043
00044
00045
00054 void init( const double* data, size_t size ) {
00055 _data.resize(size) ;
00056 _increment.resize(size) ;
00057 _max_index = size-1;
00058 _index = 0;
00059 _value = data[0];
00060 _sign = 1.0;
00061 if (_max_index == 0) {
00062 _data[0] = data[0];
00063 _increment[0] = 0.0;
00064 } else if (_max_index > 0) {
00065
00066
00067
00068 value_type left = data[1] - data[0];
00069 if (left < 0) {
00070 _sign = -1.0;
00071 }
00072 _data[0] = data[0];
00073 _increment[0] = left;
00074
00075
00076
00077 for ( size_type n = 1; n < _max_index; ++n ) {
00078 value_type right = data[n+1] - data[n];
00079 if (left * right <= 0) {
00080 throw std::invalid_argument("series not monotonic");
00081 }
00082 left = right;
00083 _data[n] = data[n];
00084 _increment[n] = left;
00085 }
00086
00087
00088
00089 _data[ _max_index ] = data[ _max_index ];
00090 _increment[ _max_index ] = left;
00091 }
00092 _index_data = _data[_index] * _sign;
00093 }
00094
00095
00096
00097
00098 public:
00099
00111 virtual size_type find_index(value_type value) {
00112
00113
00114 if (_max_index == 0) {
00115 return 0;
00116 }
00117
00118
00119 if (value == _value) {
00120 return _index;
00121 }
00122 _value = value;
00123
00124
00125
00126 value *= _sign;
00127 if (_index_data > value) {
00128
00129
00130
00131
00132 for (difference_type n = _index - 1; n >= 0 && _index_data > value; --n) {
00133 _index_data = _data[--_index] * _sign;
00134 }
00135
00136
00137
00138 } else if (_index_data < value) {
00139
00140
00141
00142
00143 difference_type N = size() - 2;
00144 for (difference_type n = _index + 1; n <= N && _index_data < value; ++n) {
00145 _index_data = _data[++_index] * _sign;
00146 }
00147
00148
00149
00150
00151 if (_index_data > value && _index > 0) {
00152 _index_data = _data[--_index] * _sign;
00153 }
00154
00155 }
00156 return _index;
00157 }
00158
00159
00160
00161
00163 virtual ~seq_data() {
00164 }
00165
00171 seq_data(size_type size) : seq_vector(size) {
00172 }
00173
00182 seq_data( const double* data, size_t size ) : seq_vector( size ) {
00183 init( data, size );
00184 }
00185
00193 template<class T, class A> seq_data( const vector<T,A> &data ) :
00194 seq_vector( data.size() ) {
00195 const size_t N = data.size();
00196 double* buffer = new double[N];
00197 std::copy( data.begin(), data.end(), buffer );
00198 init( buffer, N );
00199 delete[] buffer ;
00200 }
00201
00207 seq_data( const seq_data & copy ) :
00208 seq_vector(copy),
00209 _index(copy._index), _value(copy._value),
00210 _index_data(copy._index_data), _sign(copy._sign)
00211 {
00212 }
00213
00215 virtual seq_vector* clone() const {
00216 return new seq_data(*this);
00217 }
00218
00219 };
00220
00222 }
00223 }