GeoTessCPP: include/Profile.h Source File

GeoTessCPP 2.0.0 Software to facilitate storage and retrieval of 3D information about the Earth.

- Main Page
- Namespaces
- Classes
- Files

- File List
- File Members

All Classes Namespaces Files Functions Variables Typedefs Friends Macros
Profile.h
Go to the documentation of this file.
1 //- ****************************************************************************
2 //-
3 //- Copyright 2009 Sandia Corporation. Under the terms of Contract
4 //- DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government
5 //- retains certain rights in this software.
6 //-
7 //- BSD Open Source License.
8 //- All rights reserved.
9 //-
10 //- Redistribution and use in source and binary forms, with or without
11 //- modification, are permitted provided that the following conditions are met:
12 //-
13 //- * Redistributions of source code must retain the above copyright notice,
14 //- this list of conditions and the following disclaimer.
15 //- * Redistributions in binary form must reproduce the above copyright
16 //- notice, this list of conditions and the following disclaimer in the
17 //- documentation and/or other materials provided with the distribution.
18 //- * Neither the name of Sandia National Laboratories nor the names of its
19 //- contributors may be used to endorse or promote products derived from
20 //- this software without specific prior written permission.
21 //-
22 //- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
23 //- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 //- IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 //- ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
26 //- LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
27 //- CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
28 //- SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
29 //- INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
30 //- CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
31 //- ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32 //- POSSIBILITY OF SUCH DAMAGE.
33 //-
34 //- ****************************************************************************
35
36 #ifndef PROFILE_OBJECT_H
37 #define PROFILE_OBJECT_H
38
39 // **** _SYSTEM INCLUDES_ ******************************************************
40
41 #include <vector>
42 #include <iostream>
43 #include <string>
44 #include <fstream>
45 #include <map>
46
47 // use standard library objects
48 using namespace std;
49
50 // **** _LOCAL INCLUDES_ *******************************************************
51
52 #include "ProfileType.h"
53 #include "Data.h"
54 #include "DataArray.h"
55
56 // **** _BEGIN GEOTESS NAMESPACE_ **********************************************
57
58 namespace geotess {
59
60 // **** _FORWARD REFERENCES_ ***************************************************
61
62 class InterpolatorType;
63 class GeoTessMetaData;
64 class IFStreamAscii;
65 class IFStreamBinary;
66
67
68 // **** _CLASS DEFINITION_ *****************************************************
69
96 class GEOTESS_EXP_IMP Profile
97 {
98 private:
99
103 static int aClassCount;
104
105 public:
106
126 static Profile* newProfile(const vector<float>& radii, vector<Data*>& data);
127
128 static Profile* newProfile(const vector<float>& radii, vector<vector<double> >& data);
129 static Profile* newProfile(const vector<float>& radii, vector<vector<float> >& data);
130 static Profile* newProfile(const vector<float>& radii, vector<vector<LONG_INT> >& data);
131 static Profile* newProfile(const vector<float>& radii, vector<vector<int> >& data);
132 static Profile* newProfile(const vector<float>& radii, vector<vector<short> >& data);
133 static Profile* newProfile(const vector<float>& radii, vector<vector<byte> >& data);
134
157 static Profile* newProfile(float* radii, const int& nRadii, Data** data, const int& nData);
158
159 static Profile* newProfile(float* radii, const int& nRadii, double** values, const int& nNodes, const int& nAttributes)
160 {
161 if (nNodes < 1 && nRadii == 2)
162 return Profile::newProfile(radii, nRadii, NULL, 0);
163
164 if (nNodes == 1)
165 {
166 Data* d[1];
167 d[0] = Data::getData(values[0], nAttributes);
168 return Profile::newProfile(radii, nRadii, d, nNodes);
169 }
170
171 Data** d = new Data*[nNodes];
172 for (int i=0; i<nNodes; ++i) d[i] = Data::getData(values[i], nAttributes);
173 Profile* profile = Profile::newProfile(radii, nRadii, d, nNodes);
174 delete[] d;
175 return profile;
176 }
177
178 static Profile* newProfile(float* radii, const int& nRadii, float** values, const int& nNodes, const int& nAttributes)
179 {
180 if (nNodes < 1 && nRadii == 2)
181 return Profile::newProfile(radii, nRadii, NULL, 0);
182
183 if (nNodes == 1)
184 {
185 Data* d[1];
186 d[0] = Data::getData(values[0], nAttributes);
187 return Profile::newProfile(radii, nRadii, d, nNodes);
188 }
189
190 Data** d = new Data*[nNodes];
191 for (int i=0; i<nNodes; ++i) d[i] = Data::getData(values[i], nAttributes);
192 Profile* profile = Profile::newProfile(radii, nRadii, d, nNodes);
193 delete[] d;
194 return profile;
195 }
196
197 static Profile* newProfile(float* radii, const int& nRadii, LONG_INT** values, const int& nNodes, const int& nAttributes)
198 {
199 if (nNodes < 1 && nRadii == 2)
200 return Profile::newProfile(radii, nRadii, NULL, 0);
201
202 if (nNodes == 1)
203 {
204 Data* d[1];
205 d[0] = Data::getData(values[0], nAttributes);
206 return Profile::newProfile(radii, nRadii, d, nNodes);
207 }
208
209 Data** d = new Data*[nNodes];
210 for (int i=0; i<nNodes; ++i) d[i] = Data::getData(values[i], nAttributes);
211 Profile* profile = Profile::newProfile(radii, nRadii, d, nNodes);
212 delete[] d;
213 return profile;
214 }
215
216 static Profile* newProfile(float* radii, const int& nRadii, int** values, const int& nNodes, const int& nAttributes)
217 {
218 if (nNodes < 1 && nRadii == 2)
219 return Profile::newProfile(radii, nRadii, NULL, 0);
220
221 if (nNodes == 1)
222 {
223 Data* d[1];
224 d[0] = Data::getData(values[0], nAttributes);
225 return Profile::newProfile(radii, nRadii, d, nNodes);
226 }
227
228 Data** d = new Data*[nNodes];
229 for (int i=0; i<nNodes; ++i) d[i] = Data::getData(values[i], nAttributes);
230 Profile* profile = Profile::newProfile(radii, nRadii, d, nNodes);
231 delete[] d;
232 return profile;
233 }
234
235 static Profile* newProfile(float* radii, const int& nRadii, short** values, const int& nNodes, const int& nAttributes)
236 {
237 if (nNodes < 1 && nRadii == 2)
238 return Profile::newProfile(radii, nRadii, NULL, 0);
239
240 if (nNodes == 1)
241 {
242 Data* d[1];
243 d[0] = Data::getData(values[0], nAttributes);
244 return Profile::newProfile(radii, nRadii, d, nNodes);
245 }
246
247 Data** d = new Data*[nNodes];
248 for (int i=0; i<nNodes; ++i) d[i] = Data::getData(values[i], nAttributes);
249 Profile* profile = Profile::newProfile(radii, nRadii, d, nNodes);
250 delete[] d;
251 return profile;
252 }
253
254 static Profile* newProfile(float* radii, const int& nRadii, byte** values, const int& nNodes, const int& nAttributes)
255 {
256 if (nNodes < 1 && nRadii == 2)
257 return Profile::newProfile(radii, nRadii, NULL, 0);
258
259 if (nNodes == 1)
260 {
261 Data* d[1];
262 d[0] = Data::getData(values[0], nAttributes);
263 return Profile::newProfile(radii, nRadii, d, nNodes);
264 }
265
266 Data** d = new Data*[nNodes];
267 for (int i=0; i<nNodes; ++i) d[i] = Data::getData(values[i], nAttributes);
268 Profile* profile = Profile::newProfile(radii, nRadii, d, nNodes);
269 delete[] d;
270 return profile;
271 }
272
276 static string class_name() { return "Profile"; };
277
281 virtual int class_size() const { return (int) sizeof(Profile); };
282
286 static int class_count() { return aClassCount; };
287
293 virtual const ProfileType& getType() const = ABSTRACT;
294
299 virtual bool operator == (const Profile& p) const { return (getType() == p.getType()); }
300
305 virtual double getValue(const InterpolatorType& rInterpType,
306 int attributeIndex, double radius, bool allowRadiusOutOfRange) const = ABSTRACT;
307
312 double getValue(const vector<int>& nodeIds,
313 const vector<double>& coefficients, int attributeIndex) const
314 {
315 double value = 0;
316 for (int i=0; i<(int)nodeIds.size(); ++i)
317 value += getValue(attributeIndex, nodeIds[i])*coefficients[i];
318 return value;
319 }
320
329 virtual double getValue(int attributeIndex, int nodeIndex) const = ABSTRACT;
330
341 virtual bool isNaN(int nodeIndex, int attributeIndex) = ABSTRACT;
342
349 virtual double getValueTop(int attributeIndex) const = ABSTRACT;
350
357 virtual double getValueBottom(int attributeIndex) const
358 {
359 return getValue(attributeIndex, 0);
360 }
361
366 virtual float getRadius(int i) const = ABSTRACT;
367
373 virtual Data** getData() = ABSTRACT;
374
379 virtual Data* getData(int i) = ABSTRACT;
380
384 virtual const Data& getData(int i) const = ABSTRACT;
385
392 virtual void setData(int index, Data* data) = ABSTRACT;
393
400 virtual void setData(const vector<Data*>& inData) = ABSTRACT;
401
407 virtual void setRadii(const vector<float>& newRadii) = ABSTRACT;
408
412 virtual float getRadiusTop() const = ABSTRACT;
413
417 virtual const Data& getDataTop() const = ABSTRACT;
418
422 virtual Data* getDataTop() = ABSTRACT;
423
427 virtual float getRadiusBottom() const = ABSTRACT;
428
432 virtual const Data& getDataBottom() const = ABSTRACT;
433
437 virtual Data* getDataBottom() = ABSTRACT;
438
442 virtual int getNRadii() const = ABSTRACT;
443
447 virtual int getNData() const = ABSTRACT;
448
452 virtual float* getRadii() = ABSTRACT;
453
457 double getThickness() { return getRadiusTop() - getRadiusBottom(); }
458
464 int getRadiusIndex(double radius) const
465 { return getRadiusIndex(radius, -1); }
466
478 virtual int getRadiusIndex(double radius, int jlo) const
479 {
480 // note that ProfileNPoint will override this method.
481 return 0;
482 }
483
496 virtual double getInterpolationCoefficient(int i, double radius,
497 bool allowOutOfRange) const
498 {
499 if (!allowOutOfRange && (radius < getRadiusBottom() || radius > getRadiusTop()))
500 return NaN_DOUBLE;
501
502 // note that ProfileNPoint will override this method.
503 return 1.;
504 }
505
513 virtual int getPointIndex(int nodeIndex) const = ABSTRACT;
514
519 virtual int findClosestRadiusIndex(double radius) const = ABSTRACT;
520
522
529 virtual void getWeights(map<int, double>& weights,
530 double dkm, double radius, double hcoefficient) const
531 {
532 // get the point index of the one-and-only node.
533
534 int index = getPointIndex(0);
535
536 // find the current weight of the point, if it exists.
537 // either set the weight of pointIndex (if it does not already exist),
538 // or add the new weight to the existing weight.
539
540 map<int, double>::iterator it = weights.find(index);
541 if (it == weights.end())
542 weights[index] = dkm * hcoefficient;
543 else
544 it->second += dkm * hcoefficient;
545 }
546
553 virtual void getCoefficients(map<int, double>& coefficients, double radius,
554 double horizontalCoefficient) const
555 {
556 // this works for Profile types Constant, Thin and Surface since they only have a single node
557 // in the profile. It does not work for ProfileNPoint and ProfileEmpty so they override this method.
558
559 coefficients[getPointIndex(0)] = horizontalCoefficient;
560 }
561
565 Profile() { ++aClassCount; };
566
570 virtual ~Profile() { --aClassCount; };
571
575 static Profile* newProfile(IFStreamBinary& ifs, GeoTessMetaData& gtmd);
576
580 static Profile* newProfile(IFStreamAscii& ifs, GeoTessMetaData& gtmd);
581
585 virtual void write(IFStreamBinary& ofs) = ABSTRACT;
586
590 virtual void write(IFStreamAscii& ofs) = ABSTRACT;
591
599 virtual void setPointIndex(int nodeIndex, int pointIndex) = ABSTRACT;
600
608 virtual void resetPointIndices() = ABSTRACT;
609
610 virtual void setInterpolationCoefficients(const InterpolatorType& interpType,
611 vector<int>& nodeIndexes, vector<double>& coefficients,
612 double& radius, bool& allowOutOfRange)
613 {
614 // this code works for Profiles constant, thin and surface.
615 // ProfileNPoint and ProfileEmpty will override it.
616 nodeIndexes.push_back(0);
617 if (!allowOutOfRange && (radius < getRadiusBottom() || radius > getRadiusTop()))
618 coefficients.push_back(NaN_DOUBLE);
619 else
620 coefficients.push_back(1.);
621 }
622
626 virtual Profile* copy() = ABSTRACT;
627
629
630 }; // end class Profile
631
632 } // end namespace geotess
633
634 #endif // PROFILE_OBJECT_H