1 #ifndef LINEAR_INTERPOLATE_AD_H 2 #define LINEAR_INTERPOLATE_AD_H 21 AutoDerivative<double> >,
22 public Printable<Return1Point<AutoDerivative<double>,
23 AutoDerivative<double> > > {
32 void print(std::ostream& Os)
const { Os <<
"Return1Point"; }
46 public Printable<LinearInterpolate2Point<AutoDerivative<double>,
47 AutoDerivative<double> > > {
53 : x0_(x0), x1_(x1), y0_(y0), delta_y0_((y1 - y0) / (x1 - x0))
63 delta_y0_.value() * (x.
value() - x0_.value());
67 res.
gradient_ref() = y0_.gradient() + delta_y0_.gradient() *
68 (x.
value() - x0_.value()) - delta_y0_.value() * x0_.gradient();
69 else if(y0_.is_constant())
72 res.
gradient_ref() = y0_.gradient() + delta_y0_.gradient() *
73 (x.
value() - x0_.value()) +
74 delta_y0_.value() * (x.
gradient() - x0_.gradient());
76 void print(std::ostream& Os)
const { Os <<
"LinearInterpolate2Point"; }
91 public Printable<LinearInterpolate<AutoDerivative<double>,
92 AutoDerivative<double> > > {
95 {OUT_OF_RANGE_EXTRAPOLATE = 0, OUT_OF_RANGE_CLIP, OUT_OF_RANGE_ERROR};
105 : out_of_range(Out_of_range), nvar(0)
108 if(std::distance(xstart, xend) == 0) {
113 nvar = std::max(xstart->number_variable(), ystart->number_variable());
114 if(std::distance(xstart, xend) == 1) {
128 throw Exception(
"x0 and y0 need to have the same number of variables");
134 }
else while(xstart != xend) {
147 throw Exception(
"All X and Y need to have the same number of variables");
149 throw Exception(
"All X and Y need to have the same number of variables");
164 throw Exception(
"All X and Y need to have the same number of variables");
166 throw Exception(
"All X and Y need to have the same number of variables");
181 interpolate(x, res2);
192 throw Exception(
"Can not interpolate since interpolation map is empty.");
197 const_iterator Itype;
198 Itype i = inter.lower_bound(x);
199 if(i == inter.end()) {
200 switch(out_of_range) {
201 case OUT_OF_RANGE_ERROR:
203 std::stringstream err_msg;
204 err_msg <<
"Linear interpolation AD point " 205 << x.
value() <<
" is past the end of interpolation range: " 206 <<
"[" << inter.begin()->first.value()
207 <<
", " << inter.rbegin()->first.value() <<
"]";
210 case OUT_OF_RANGE_EXTRAPOLATE:
211 inter.rbegin()->second->interpolate(x, res);
213 case OUT_OF_RANGE_CLIP:
214 inter.rbegin()->second->interpolate(inter.rbegin()->second->x_max(),
218 throw Exception(
"Unknown out_of_range value");
221 if(x >= i->second->x_min())
222 i->second->interpolate(x, res);
224 switch(out_of_range) {
225 case OUT_OF_RANGE_ERROR:
227 std::stringstream err_msg;
228 err_msg <<
"Linear interpolation AD point " 229 << x.
value() <<
" is outside of interpolation range: " 230 <<
"[" << inter.begin()->first.value()
231 <<
", " << inter.rbegin()->first.value() <<
"]";
234 case OUT_OF_RANGE_EXTRAPOLATE:
235 i->second->interpolate(x, res);
237 case OUT_OF_RANGE_CLIP:
238 i->second->interpolate(i->second->x_min(), res);
241 throw Exception(
"Unknown out_of_range value");
245 void print(std::ostream& Os)
const { Os <<
"LinearInterpolate"; }
#define range_max_check(V, Max)
Range check.
void print(std::ostream &Os) const
bool is_constant() const
Is this object a constant (with a gradient() all zeros)?
This just returns the same y value, always.
LinearInterpolate2Point(const AutoDerivative< double > &x0, const AutoDerivative< double > &y0, const AutoDerivative< double > &x1, const AutoDerivative< double > &y1)
This class takes a set of points and values, and linearly interpolates between those values...
This is the base of the exception hierarchy for Full Physics code.
void print(std::ostream &Os) const
blitz::Array< T, 1 > & gradient_ref() const
Helper class that gives us a reference that we can assign a AutoDerivative to and write into the corr...
AutoDerivative< double > operator()(const AutoDerivative< double > &x) const
This is a Mixin for classes that can be printed.
Interface for interpolating values.
void interpolate(const AutoDerivative< double > &x, const AutoDerivativeRef< double > &res) const
void interpolate(const AutoDerivative< double > &x, const AutoDerivativeRef< double > &res) const
This does linear interpolate between two points.
There are a number of tools that can be used to do "Automatic Differentiation" (see for example http:...
LinearInterpolate(I1 xstart, I1 xend, I2 ystart, BehaviorOutOfRange Out_of_range=OUT_OF_RANGE_EXTRAPOLATE)
Constructor.
int number_variable() const
Number of variables in gradient.
const blitz::Array< T, 1 > & gradient() const
Gradient.
virtual void interpolate(const AutoDerivative< double > &x, const AutoDerivativeRef< double > &res) const
const AutoDerivative< double > & x_max() const
virtual const TX & x_min() const =0
const AutoDerivative< double > & x_max() const
Contains classes to abstract away details in various Spurr Radiative Transfer software.
const T & value() const
Convert to type T.
void print(std::ostream &Os) const
Return1Point(const AutoDerivative< double > &x0, const AutoDerivative< double > &y0)
virtual const TX & x_max() const =0
const AutoDerivative< double > & x_min() const
const AutoDerivative< double > & x_min() const