fc5930c1b4faa1730c69bf3d0f86145bd8e5ac6c
[blender.git] / intern / iksolver / intern / TNT / vecadaptor.h
1 /**
2  * $Id$
3  */
4
5 /*
6
7 *
8 * Template Numerical Toolkit (TNT): Linear Algebra Module
9 *
10 * Mathematical and Computational Sciences Division
11 * National Institute of Technology,
12 * Gaithersburg, MD USA
13 *
14 *
15 * This software was developed at the National Institute of Standards and
16 * Technology (NIST) by employees of the Federal Government in the course
17 * of their official duties. Pursuant to title 17 Section 105 of the
18 * United States Code, this software is not subject to copyright protection
19 * and is in the public domain.  The Template Numerical Toolkit (TNT) is
20 * an experimental system.  NIST assumes no responsibility whatsoever for
21 * its use by other parties, and makes no guarantees, expressed or implied,
22 * about its quality, reliability, or any other characteristic.
23 *
24 * BETA VERSION INCOMPLETE AND SUBJECT TO CHANGE
25 * see http://math.nist.gov/tnt for latest updates.
26 *
27 */
28
29
30
31 #ifndef VECADAPTOR_H
32 #define VECADAPTOR_H
33
34 #include <cstdlib>
35 #include <iostream>
36 #include <strstream>
37 #include <cassert>
38
39 #include "subscript.h"
40
41 #ifdef TNT_USE_REGIONS
42 #include "region1d.h"
43 #endif
44
45 namespace TNT
46 {
47
48 //  see "tntreq.h" for TNT requirements for underlying vector
49 //  class.  This need NOT be the STL vector<> class, but a subset
50 //  that provides minimal services.
51 //
52 //  This is a container adaptor that provides the following services.
53 //
54 //      o)  adds 1-offset operator() access ([] is always 0 offset)
55 //      o)  adds TNT_BOUNDS_CHECK to () and []
56 //      o)  adds initialization from strings, e.g.  "1.0 2.0 3.0";
57 //      o)  adds newsize(N) function (does not preserve previous values)
58 //      o)  adds dim() and dim(1)
59 //      o)  adds free() function to release memory used by vector
60 //      o)  adds regions, e.g. A(Index(1,10)) = ... 
61 //      o)  add getVector() method to return adapted container
62 //      o)  adds simple I/O for ostreams
63
64 template <class BBVec>
65 class Vector_Adaptor
66 {
67
68   public:
69     typedef   typename BBVec::value_type T;
70     typedef         T   value_type;
71     typedef         T   element_type;
72     typedef         T*  pointer;
73     typedef         T*  iterator;
74     typedef         T&  reference;
75     typedef const   T*  const_iterator;
76     typedef const   T&  const_reference;
77     
78     Subscript lbound() const { return 1; }
79
80   protected:
81     BBVec v_;
82     T* vm1_;
83
84   public:
85
86     Subscript size() const { return v_.size(); }
87
88     // These were removed so that the ANSI C++ valarray class
89     // would work as a possible storage container.
90     //
91     //
92     //iterator begin() { return v_.begin();}
93     //iterator begin() { return &v_[0];}
94     //
95     //iterator end()   { return v_.end(); }
96     //iterator end()   { return &v_[0] + v_.size(); }
97     //
98     //const_iterator begin() const { return v_.begin();}
99     //const_iterator begin() const { return &v_[0];}
100     //
101     //const_iterator end()  const { return v_.end(); }
102     //const_iterator end()  const { return &v_[0] + v_.size(); }
103
104     BBVec& getVector() { return v_; }
105     Subscript dim() const { return v_.size(); }
106     Subscript dim(Subscript i)
107     {
108 #ifdef TNT_BOUNDS_CHECK
109         assert(i==TNT_BASE_OFFSET);
110 #endif
111         return (i==TNT_BASE_OFFSET ? v_.size() : 0 );
112     }
113     Vector_Adaptor() : v_() {};
114     Vector_Adaptor(const Vector_Adaptor<BBVec> &A) : v_(A.v_) 
115     { 
116         vm1_ = ( v_.size() > 0 ? &(v_[0]) -1 : NULL); 
117
118     } 
119
120     Vector_Adaptor(Subscript N, /*const*/ char *s) : v_(N) 
121     {
122         istrstream ins(s);
123         for (Subscript i=0; i<N; i++)
124             ins >> v_[i] ;
125
126         vm1_ = ( v_.size() > 0 ? &(v_[0]) -1 : NULL); 
127     }; 
128
129     Vector_Adaptor(Subscript N, const T& value = T()) : v_(N)
130     {
131         for (Subscript i=0; i<N; i++)
132              v_[i]  = value;
133         
134         vm1_ = ( v_.size() > 0 ? &(v_[0]) -1 : NULL); 
135     }
136
137     Vector_Adaptor(Subscript N, const T* values) : v_(N)
138     {
139         for (Subscript i=0; i<N; i++)
140              v_[i]  = values[i];
141         vm1_ = ( v_.size() > 0 ? &(v_[0]) -1 : NULL); 
142     } 
143     Vector_Adaptor(const BBVec & A) : v_(A) 
144     {
145         vm1_ = ( v_.size() > 0 ? &(v_[0]) -1 : NULL); 
146     }
147
148     // NOTE: this assumes that BBVec(0) constructor creates an 
149     //  null vector that does not take up space...  It would be
150     //  great to require that BBVec have a corresponding free()
151     //  function, but in particular STL vectors do not.
152     //
153     Vector_Adaptor<BBVec>& free()
154     {
155         return *this = Vector_Adaptor<BBVec>(0);
156     }
157
158     Vector_Adaptor<BBVec>& operator=(const Vector_Adaptor<BBVec> &A) 
159     { 
160         v_ = A.v_ ; 
161         vm1_ = ( v_.size() > 0 ? &(v_[0]) -1 : NULL); 
162         return *this;
163     }
164
165     Vector_Adaptor<BBVec>& newsize(Subscript N)
166     {
167         // NOTE: this is not as efficient as it could be
168         // but to retain compatiblity with STL interface
169         // we cannot assume underlying implementation
170         // has a newsize() function.
171
172         return *this = Vector_Adaptor<BBVec>(N);
173
174     }
175
176     Vector_Adaptor<BBVec>& operator=(const T &a) 
177     {
178         Subscript i;
179         Subscript N = v_.size();    
180         for (i=0; i<N; i++)
181             v_[i] = a;
182
183         return *this;
184     }
185
186     Vector_Adaptor<BBVec>& resize(Subscript N) 
187     { 
188         if (N == size()) return *this;
189
190         Vector_Adaptor<BBVec> tmp(N);
191         Subscript n =  (N < size() ? N : size());  // min(N, size());
192         Subscript i;
193
194         for (i=0; i<n; i++)
195             tmp[i] = v_[i];
196             
197
198         return (*this = tmp);
199
200     }
201
202
203     reference operator()(Subscript i)
204     { 
205 #ifdef TNT_BOUNDS_CHECK
206         assert(1<=i);
207         assert(i<=dim());
208 #endif
209         return vm1_[i]; 
210     }
211
212     const_reference operator()(Subscript i) const
213     { 
214 #ifdef TNT_BOUNDS_CHECK
215         assert(1<=i);
216         assert(i<=dim());
217 #endif
218         return vm1_[i]; 
219     }
220
221     reference operator[](Subscript i)
222     { 
223 #ifdef TNT_BOUNDS_CHECK
224         assert(0<=i);
225         assert(i<dim());
226 #endif
227         return v_[i]; 
228     }
229
230     const_reference operator[](Subscript i) const
231     { 
232 #ifdef TNT_BOUNDS_CHECK
233         assert(0<=i);
234         assert(i<dim());
235 #endif
236         return v_[i]; 
237     }
238
239
240 #ifdef TNT_USE_REGIONS
241     // "index-aware" features, all of these are 1-based offsets
242
243     typedef Region1D<Vector_Adaptor<BBVec> > Region;
244
245     typedef const_Region1D< Vector_Adaptor<BBVec> > const_Region;
246
247     Region operator()(const Index1D &I)
248     {   return Region(*this, I); }
249
250     Region operator()(const Subscript i1, Subscript i2)
251     {   return Region(*this, i1, i2); }
252
253     const_Region operator()(const Index1D &I) const
254     {   return const_Region(*this, I); }
255
256     const_Region operator()(const Subscript i1, Subscript i2) const
257     {   return const_Region(*this, i1, i2); }
258 #endif
259 // TNT_USE_REGIONS
260
261
262 };
263
264 #include <iostream>
265
266 template <class BBVec>
267 std::ostream& operator<<(std::ostream &s, const Vector_Adaptor<BBVec> &A)
268 {
269     Subscript M=A.size();
270
271     s << M << endl;
272     for (Subscript i=1; i<=M; i++)
273             s << A(i) << endl;
274     return s;
275 }
276
277 template <class BBVec>
278 std::istream& operator>>(std::istream &s, Vector_Adaptor<BBVec> &A)
279 {
280     Subscript N;
281     
282     s >> N;
283
284     A.resize(N);
285
286     for (Subscript i=1; i<=N; i++)
287         s >> A(i);
288
289     return s;
290 }
291
292 } // namespace TNT
293
294 #endif
295