Loading...
Searching...
No Matches
ValueScaling.h
1/*
2
3MIT License
4
5Copyright (c) 2017 FMI Open Development / Markus Peura, first.last@fmi.fi
6
7Permission is hereby granted, free of charge, to any person obtaining a copy
8of this software and associated documentation files (the "Software"), to deal
9in the Software without restriction, including without limitation the rights
10to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11copies of the Software, and to permit persons to whom the Software is
12furnished to do so, subject to the following conditions:
13
14The above copyright notice and this permission notice shall be included in all
15copies or substantial portions of the Software.
16
17THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23SOFTWARE.
24
25*/
26/*
27Part of Rack development has been done in the BALTRAD projects part-financed
28by the European Union (European Regional Development Fund and European
29Neighbourhood Partnership Instrument, Baltic Sea Region Programme 2007-2013)
30*/
31#ifndef IMAGE_SCALING2_H_
32#define IMAGE_SCALING2_H_ "ImageScaling 0.1, 2017/09 Markus.Peura@fmi.fi"
33
34#include <drain/Type.h>
35#include <drain/TypeUtils.h>
36#include <drain/UniTuple.h>
37#include <stddef.h> // size_t
38
39#include "Range.h"
40
41//#include "Geometry.h"
42//#include "Coordinates.h"
43
44
45namespace drain
46{
47
48
49//extern drain::Log iLog;
50
51// If the intensities of the image correspond to a physical value (like temperature), this is the recommended way to copy.
52
54
64class ValueScaling : public UniTuple<double,2> { // UniTuple<double,4>{
65public:
66
68 double & scale;
69
71 double & offset;
72
75
76
77 inline
78 ValueScaling(double scale=1.0, double offset = 0.0) : // RANGE ok? double scaleOut=1.0, double offsetOut=0.0) :
79 scale(this->next()), offset(this->next()) //, physRange(this->tuple(), 2)
80 {
81 //setConversionScale(scale, offset, scaleOut, offsetOut);
83 physRange.set(0,0);
84 };
85
86 inline
87 ValueScaling(double scale, double offset, const drain::Range<double> & range) : //, double scaleOut=1.0, double offsetOut=0.0) :
88 scale(this->next()), offset(this->next()) //, physRange(this->tuple(), 2)
89 {
90 //setConversionScale(scale, offset, scaleOut, offsetOut);
92 physRange.set(range); // TODO tune: scaleOut, offsetOut
93 };
94
95 inline
96 ValueScaling(const drain::ValueScaling & scaling) :
97 scale(this->next()), offset(this->next()) //, physRange(this->tuple(), 2)
98 {
99 this->assignSequence(scaling);
100 physRange.set(scaling.physRange);
101 };
102
103 //
104 inline
105 ValueScaling(const drain::UniTuple<double,2> & scaling) :
106 scale(this->next()), offset(this->next())
107 {
108 setScaling(scaling[0], scaling[1]);
109 };
110
111
112 // Conversion scaling
113 inline
114 ValueScaling(const drain::ValueScaling & scalingIn, const drain::ValueScaling & scalingOut) :
115 scale(this->next()), offset(this->next())
116 {
117 setConversionScale(scalingIn, scalingOut);
118 // physRange??? intersection / union
119 };
120
121 virtual inline
122 ~ValueScaling(){};
123
124
125 inline
126 ValueScaling & operator=(const drain::ValueScaling & scaling){
127 if (&scaling != this){
128 this->assignSequence(scaling);
129 physRange.set(scaling.physRange);
130 }
131 return *this;
132 }
133
135 virtual inline
136 void setScaling(double scale, double offset){
137 this->set(scale, offset); // virtual IMPORTANT for channels/view
138 }
139
140 virtual
141 void setScaling(const ValueScaling & scaling){
142 this->assignSequence(scaling);
143 }
144
146 virtual inline // LATER: scalingPtr!
147 const ValueScaling & getScaling() const {
148 return *this;
149 }
150
152 virtual inline // LATER: scalingPtr!
154 return *this;
155 }
156
157
158
160 inline
162 set(1.0, 0.0);
163 }
164
166
172 inline
173 void setNormalScale(const std::type_info & t){
174 if (Type::call<drain::typeIsSmallInt>(t))
175 set(1.0/drain::Type::call<drain::typeMax,double>(t), 0.0);
176 else // warn? (esp. for int and long int)
177 set(1.0, 0.0); // absolute scale
178 }
179
181 inline
182 void setConversionScale(double scale, double offset = 0.0, double scaleOut=1.0, double offsetOut=0.0){
183 set(scale/scaleOut, (offset - offsetOut)/scaleOut);
184 }
185
187 inline
189 set(s2.scale/s1.scale, (s2.offset-s1.offset) / s1.scale);
190 }
191
192 //template <typename T>
193 inline
194 void setConversionScale(const Range<double> & r1, const Range<double> & r2){
195 set(r2.width()/r1.width(), r2.min - r2.width()/r1.width()*r1.min);
196 }
197
199 void setOptimalScale(const std::type_info & t);
200
201
203 inline
204 void setPhysicalScale(const std::type_info & t, double min, double max){
205 setPhysicalRange(min, max);
207 }
208
210
213 inline
214 void setPhysicalScale(const std::type_info & t, const drain::ValueScaling & scaling){
217 };
218
220 inline
221 const Range<double> & getPhysicalRange() const { // , const std::string &unit ?
222 return physRange;
223 }
224
226 inline
227 Range<double> & getPhysicalRange() { // , const std::string &unit ?
228 return physRange;
229 }
230
232 inline
233 void setPhysicalMax(double max){ // dangerous (after min?)
234 setPhysicalRange(0.0, max);
235 }
236
238 template <class T>
239 inline
240 void setPhysicalRange(const Range<T> &range){ // , const std::string &unit ?
242 }
243
245 inline
246 void setPhysicalRange(double min, double max){ // , const std::string &unit ?
247 physRange.set(min,max);
248 }
249
251 inline
252 double getScale() const { return scale; }
253
255 inline
256 double getOffset() const { return offset; }
257
259
262 inline
263 bool isScaled() const {
264 return (scale!=1.0) || (offset!=0.0);
265 }
266
268 inline
269 double getMinPhys() const {
270 return physRange.min;
271 }
272
274 inline
275 double getMaxPhys() const {
276 return physRange.max;
277 }
278
280 inline
281 bool isPhysical() const {
282 return (!physRange.empty());
283 }
284
286 /* short => float
287 *
288 */
289 //inline
290 void adoptScaling(const drain::ValueScaling & srcScaling, const std::type_info & srcType, const std::type_info & dstType = typeid(void));
291
292
294 inline
295 double fwd(double x) const {
296 return scale*x + offset;
297 }
298
300 inline
301 double inv(double y) const {
302 return (y - offset) / scale;
303 }
304
305 virtual inline
306 void toStream(std::ostream & ostr) const override {
307 ostr << scale << ',' << offset;
308 if (isPhysical())
309 ostr << " [" << physRange << ']';
310 }
311
312 inline
313 std::string str() const{
314 std::stringstream sstr;
315 toStream(sstr);
316 return sstr.str();
317 }
318
319
320
321};
322
323inline
324std::ostream & operator<<(std::ostream &ostr, const drain::ValueScaling & s){
325 s.toStream(ostr);
326 return ostr;
327}
328
329} // drain::
330
331#endif
332
333// Drain
Definition Range.h:52
tuplebase_t & assignSequence(T &sequence, bool LENIENT=false)
Proposed for tuples only; derived classes should not shadow this.
Definition TupleBase.h:287
Tuple of N elements of type T.
Definition UniTuple.h:65
Linear scaling and physical range for image intensities.
Definition ValueScaling.h:64
double & scale
Multiplicative coefficient \i a in: y = ax + b.
Definition ValueScaling.h:68
void setPhysicalRange(double min, double max)
Sets the supported range for physical values. Does not change scaling or type.
Definition ValueScaling.h:246
const Range< double > & getPhysicalRange() const
Returns a typical or supported range for physical values.
Definition ValueScaling.h:221
double getMinPhys() const
Returns the minimum physical value.
Definition ValueScaling.h:269
drain::Range< double > physRange
Minimum and maximum physical value of the imaged quantity (not limited to corresponding to minCodeVal...
Definition ValueScaling.h:74
virtual ValueScaling & getScaling()
Get linear scaling.
Definition ValueScaling.h:153
bool isPhysical() const
Returns true, physical intensity range has been set.
Definition ValueScaling.h:281
bool isScaled() const
Returns true, if scaling has effect ie. scale!=1.0 or offset!=0.0.
Definition ValueScaling.h:263
void setAbsoluteScale()
If the intensities of the image correspond to an absolute value (like count) then the scale should be...
Definition ValueScaling.h:161
double fwd(double x) const
Forward scaling: given encoded value x, returns corresponding value (possibly physically meaningful).
Definition ValueScaling.h:295
double & offset
Additive coefficient \i b in: y = ax + b.
Definition ValueScaling.h:71
void setPhysicalRange(const Range< T > &range)
Sets the supported range for physical values. Does not change scaling or type.
Definition ValueScaling.h:240
double getOffset() const
Returns the intensity scaling offset, ie. b in a*x + b . See set setScale()
Definition ValueScaling.h:256
Range< double > & getPhysicalRange()
Returns a typical or supported range for physical values. Modifying the range will not change scaling...
Definition ValueScaling.h:227
void setConversionScale(double scale, double offset=0.0, double scaleOut=1.0, double offsetOut=0.0)
If the intensities of the image correspond to a physical value (like temperature),...
Definition ValueScaling.h:182
void setPhysicalMax(double max)
In integer-valued images, set the physical values corresponding to [0, maxCodeValue].
Definition ValueScaling.h:233
double getMaxPhys() const
Returns the maximum physical value.
Definition ValueScaling.h:275
void setNormalScale(const std::type_info &t)
For "small integer" types, resets offset and scale such that maximum code value corresponds to 1....
Definition ValueScaling.h:173
void setConversionScale(const drain::ValueScaling &s1, const drain::ValueScaling &s2)
Set scaling for which scaling.inv(x) = s2.inv(s1.fwd(x))
Definition ValueScaling.h:188
void adoptScaling(const drain::ValueScaling &srcScaling, const std::type_info &srcType, const std::type_info &dstType=typeid(void))
Sets scale and offset according to physical range and current type.
Definition ValueScaling.cpp:73
virtual void setScaling(double scale, double offset)
Set linear scaling.
Definition ValueScaling.h:136
void setPhysicalScale(const std::type_info &t, const drain::ValueScaling &scaling)
Sets physical range (min, max) and scales storage type accordingly.
Definition ValueScaling.h:214
double inv(double y) const
Inverse scaling: given physically meaningful value y, returns the corresponding code value.
Definition ValueScaling.h:301
void setOptimalScale(const std::type_info &t)
If storage type is integer, adjust scale such that resolution is maximized.
Definition ValueScaling.cpp:36
void setPhysicalScale(const std::type_info &t, double min, double max)
Sets physical range (min, max) and scales storage type accordingly.
Definition ValueScaling.h:204
virtual const ValueScaling & getScaling() const
Get linear scaling.
Definition ValueScaling.h:147
double getScale() const
Returns the intensity scaling factor. See set setScale()
Definition ValueScaling.h:252
Definition DataSelector.cpp:1277