LSSTApplications  10.0-2-g4f67435,11.0.rc2+1,11.0.rc2+12,11.0.rc2+3,11.0.rc2+4,11.0.rc2+5,11.0.rc2+6,11.0.rc2+7,11.0.rc2+8
LSSTDataManagementBasePackage
Function.h
Go to the documentation of this file.
1 // -*- LSST-C++ -*-
2 
3 /*
4  * LSST Data Management System
5  * Copyright 2008, 2009, 2010 LSST Corporation.
6  *
7  * This product includes software developed by the
8  * LSST Project (http://www.lsst.org/).
9  *
10  * This program is free software: you can redistribute it and/or modify
11  * it under the terms of the GNU General Public License as published by
12  * the Free Software Foundation, either version 3 of the License, or
13  * (at your option) any later version.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18  * GNU General Public License for more details.
19  *
20  * You should have received a copy of the LSST License Statement and
21  * the GNU General Public License along with this program. If not,
22  * see <http://www.lsstcorp.org/LegalNotices/>.
23  */
24 
25 #ifndef LSST_AFW_MATH_FUNCTION_H
26 #define LSST_AFW_MATH_FUNCTION_H
27 
36 #include <stdexcept>
37 #include <sstream>
38 #include <vector>
39 
40 #include "boost/format.hpp"
41 #include "boost/serialization/nvp.hpp"
42 #include "boost/serialization/vector.hpp"
43 #include "boost/serialization/void_cast.hpp"
44 #include "boost/serialization/export.hpp"
45 
46 #include "lsst/daf/base/Citizen.h"
47 #include "lsst/pex/exceptions.h"
48 
50 
51 namespace lsst {
52 namespace afw {
53 namespace math {
54 
55 #ifndef SWIG
56 using boost::serialization::make_nvp;
57 #endif
58 
88  template<typename ReturnT>
90  public afw::table::io::PersistableFacade< Function<ReturnT> >,
92  {
93  public:
99  explicit Function(
100  unsigned int nParams)
101  :
102  lsst::daf::base::Citizen(typeid(this)),
103  _params(nParams),
104  _isCacheValid(false)
105  {}
106 
110  explicit Function(
111  std::vector<double> const &params)
112  :
113  lsst::daf::base::Citizen(typeid(this)),
114  _params(params),
115  _isCacheValid(false)
116  {}
117 
118  virtual ~Function() {}
119 
125  unsigned int getNParameters() const {
126  return _params.size();
127  }
128 
134  virtual double getParameter(
135  unsigned int ind)
136  const {
137  return _params[ind];
138  }
139 
145  std::vector<double> const &getParameters() const {
146  return _params;
147  }
148 
156  virtual bool isLinearCombination() const { return false; }
157 
162  unsigned int ind,
163  double newValue)
164  {
165  _isCacheValid = false;
166  _params[ind] = newValue;
167  }
168 
176  std::vector<double> const &params)
177  {
178  if (_params.size() != params.size()) {
179  throw LSST_EXCEPT(pexExcept::InvalidParameterError,
180  (boost::format("params has %d entries instead of %d") % \
181  params.size() % _params.size()).str());
182  }
183  _isCacheValid = false;
184  _params = params;
185  }
186 
192  virtual std::string toString(std::string const&) const {
193  std::stringstream os;
194  os << "parameters: [ ";
195  for (std::vector<double>::const_iterator i = _params.begin(); i != _params.end(); ++i) {
196  if (i != _params.begin()) os << ", ";
197  os << *i;
198  }
199  os << " ]";
200  return os.str();
201  }
202 
203  protected:
204  std::vector<double> _params;
205  mutable bool _isCacheValid;
206 
207  virtual std::string getPythonModule() const { return "lsst.afw.math"; }
208 
209  /* Default constructor: intended only for serialization */
210  explicit Function() : lsst::daf::base::Citizen(typeid(this)), _params(0), _isCacheValid(false) {}
211 
212  private: // serialization support
213  friend class boost::serialization::access;
214  template <class Archive>
215  void serialize(Archive& ar, unsigned int const version) {
216  ar & make_nvp("params", _params);
217  }
218  };
219 
220 
228  template<typename ReturnT>
229  class Function1 : public afw::table::io::PersistableFacade< Function1<ReturnT> >,
230  public Function<ReturnT>
231  {
232  public:
233  typedef boost::shared_ptr<Function1<ReturnT> > Ptr;
234 
240  explicit Function1(
241  unsigned int nParams)
242  :
243  Function<ReturnT>(nParams)
244  {}
245 
249  explicit Function1(
250  std::vector<double> const &params)
251  :
252  Function<ReturnT>(params)
253  {}
254 
255  virtual ~Function1() {}
256 
268  virtual Ptr clone() const = 0;
269 
270  virtual ReturnT operator() (double x) const = 0;
271 
272  virtual std::string toString(std::string const& prefix="") const {
273  return std::string("Function1: ") + Function<ReturnT>::toString(prefix);
274  }
275 
276  virtual void computeCache(int const n) {}
277 
278  protected:
279  /* Default constructor: intended only for serialization */
280  explicit Function1() : Function<ReturnT>() {}
281 
282  private: // serialization
283  friend class boost::serialization::access;
284 #ifndef SWIG // SWIG doesn't like base_object
285  template <class Archive>
286  void serialize(Archive& ar, unsigned const int version) {
287  ar & make_nvp("fn", boost::serialization::base_object<Function<ReturnT> >(*this));
288  }
289 #endif
290  };
291 
299  template<typename ReturnT>
300  class Function2 : public afw::table::io::PersistableFacade< Function2<ReturnT> >,
301  public Function<ReturnT>
302  {
303  public:
304  typedef boost::shared_ptr<Function2<ReturnT> > Ptr;
305 
311  explicit Function2(
312  unsigned int nParams)
313  :
314  Function<ReturnT>(nParams)
315  {}
316 
322  explicit Function2(
323  std::vector<double> const &params)
324  :
325  Function<ReturnT>(params)
326  {}
327 
328  virtual ~Function2() {}
329 
341  virtual Ptr clone() const = 0;
342 
343  virtual ReturnT operator() (double x, double y) const = 0;
344 
345  virtual std::string toString(std::string const& prefix="") const {
346  return std::string("Function2: ") + Function<ReturnT>::toString(prefix);
347  }
351  virtual std::vector<double> getDFuncDParameters(double, double) const {
352  throw LSST_EXCEPT(lsst::pex::exceptions::NotFoundError,
353  "getDFuncDParameters is not implemented for this class");
354  }
355 
356  protected:
357  /* Default constructor: intended only for serialization */
358  explicit Function2() : Function<ReturnT>() {}
359 
360  private:
361  friend class boost::serialization::access;
362 #ifndef SWIG // SWIG doesn't like base_object
363  template <class Archive>
364  void serialize(Archive& ar, unsigned const int version) {
365  ar & make_nvp("fn", boost::serialization::base_object<Function<ReturnT> >(*this));
366  }
367 #endif
368  };
369 
370 
383  template<typename ReturnT>
384  class BasePolynomialFunction2: public Function2<ReturnT> {
385  public:
387 
396  unsigned int order)
397  :
399  _order(order)
400  {}
401 
411  std::vector<double> params)
412  :
413  Function2<ReturnT>(params),
414  _order(BasePolynomialFunction2::orderFromNParameters(static_cast<int>(params.size())))
415  {}
416 
418 
422  int getOrder() const { return _order; }
423 
424  virtual bool isLinearCombination() const { return true; }
425 
431  static int nParametersFromOrder(int order) {
432  if (order < 0) {
433  std::ostringstream os;
434  os << "order=" << order << " invalid: must be >= 0";
435  throw LSST_EXCEPT(lsst::pex::exceptions::InvalidParameterError, os.str());
436  }
437  return (order + 1) * (order + 2) / 2;
438  }
439 
454  static int orderFromNParameters(int nParameters) {
455  int order = static_cast<int>(
456  0.5 + ((-3.0 + (std::sqrt(1.0 + (8.0 * static_cast<double>(nParameters))))) / 2.0));
457  if (nParameters != BasePolynomialFunction2::nParametersFromOrder(order)) {
458  std::ostringstream os;
459  os << "nParameters=" << nParameters << " invalid: order is not an integer";
460  throw LSST_EXCEPT(lsst::pex::exceptions::InvalidParameterError, os.str());
461  }
462  return order;
463  }
464 
473  virtual std::vector<double> getDFuncDParameters(double x, double y) const {
474  unsigned int const numParams = this->getNParameters(); // Number of parameters
475  std::vector<double> deriv(numParams); // Derivatives, to return
476 
477  Function2Ptr dummy = this->clone(); // Dummy function to evaluate for derivatives
478  for (unsigned int i = 0; i < numParams; ++i) {
479  dummy->setParameter(i, 0.0);
480  }
481 
482  for (unsigned int i = 0; i < numParams; ++i) {
483  dummy->setParameter(i, 1.0);
484  deriv[i] = (*dummy)(x, y);
485  dummy->setParameter(i, 0.0);
486  }
487 
488  return deriv;
489  }
490 
491  protected:
492  int _order;
493 
494  /* Default constructor: intended only for serialization */
495  explicit BasePolynomialFunction2() : Function2<ReturnT>(1), _order(0) {}
496 
497  private:
499 #ifndef SWIG // SWIG doesn't like base_object
500  template <class Archive>
501  void serialize(Archive& ar, unsigned const int version) {
502  ar & make_nvp("fn2", boost::serialization::base_object<Function2<ReturnT> >(*this));
503  ar & make_nvp("order", _order);
504  }
505 #endif
506  };
507 
508 
512  template<typename ReturnT>
513  class NullFunction1 : public Function1<ReturnT> {
514  public:
515  explicit NullFunction1() : Function1<ReturnT>(0) {}
516  typename Function1<ReturnT>::Ptr clone() const {
517  return typename Function1<ReturnT>::Ptr(new NullFunction1()); }
518 
519  private:
520  ReturnT operator() (double) const { return static_cast<ReturnT>(0); }
521 
522  private:
524 #ifndef SWIG // SWIG doesn't like base_object
525  template <class Archive>
526  void serialize(Archive& ar, unsigned int const version) {
527  ar & make_nvp("fn1", boost::serialization::base_object<Function1<ReturnT> >(*this));
528  }
529 #endif
530  };
531 
535  template<typename ReturnT>
536  class NullFunction2 : public Function2<ReturnT> {
537  public:
538  explicit NullFunction2() : Function2<ReturnT>(0) {}
539  typename Function2<ReturnT>::Ptr clone() const {
540  return typename Function2<ReturnT>::Ptr(new NullFunction2()); }
541 
542  private:
543  ReturnT operator() (double, double) const { return static_cast<ReturnT>(0); }
544 
545  private:
547 #ifndef SWIG // SWIG doesn't like base_object
548  template <class Archive>
549  void serialize(Archive& ar, unsigned int const version) {
550  ar & make_nvp("fn2", boost::serialization::base_object<Function2<ReturnT> >(*this));
551  }
552 #endif
553  };
554 
555 
556 }}} // lsst::afw::math
557 
558 #endif // #ifndef LSST_AFW_MATH_FUNCTION_H
int y
virtual Ptr clone() const =0
Return a pointer to a deep copy of this function.
friend class boost::serialization::access
Definition: Function.h:523
int _order
order of polynomial
Definition: Function.h:492
Function(unsigned int nParams)
Construct a Function given the number of function parameters.
Definition: Function.h:99
virtual std::string toString(std::string const &prefix="") const
Return a string representation of the function.
Definition: Function.h:272
virtual std::string getPythonModule() const
Return the fully-qualified Python module that should be imported to guarantee that its factory is reg...
Definition: Function.h:207
void serialize(Archive &ar, unsigned int const version)
Definition: Function.h:526
virtual std::vector< double > getDFuncDParameters(double, double) const
Definition: Function.h:351
std::vector< double > const & getParameters() const
Return all function parameters.
Definition: Function.h:145
void serialize(Archive &ar, unsigned int const version)
Definition: Function.h:215
virtual double getParameter(unsigned int ind) const
Get one function parameter without range checking.
Definition: Function.h:134
int getOrder() const
Get the polynomial order.
Definition: Function.h:422
virtual std::string toString(std::string const &prefix="") const
Return a string representation of the function.
Definition: Function.h:345
void setParameter(unsigned int ind, double newValue)
Set one function parameter without range checking.
Definition: Function.h:161
friend class boost::serialization::access
Definition: Function.h:498
virtual bool isLinearCombination() const
Is the function a linear combination of its parameters?
Definition: Function.h:424
Function2< ReturnT >::Ptr Function2Ptr
Definition: Function.h:386
A Function taking two arguments.
Definition: Function.h:300
Base class for 2-dimensional polynomials of the form:
Definition: Function.h:384
unsigned int getNParameters() const
Return the number of function parameters.
Definition: Function.h:125
A base class for objects that can be persisted via afw::table::io Archive classes.
Definition: Persistable.h:74
Function1(std::vector< double > const &params)
Construct a Function1 given the function parameters.
Definition: Function.h:249
static int nParametersFromOrder(int order)
Compute number of parameters from polynomial order.
Definition: Function.h:431
virtual std::vector< double > getDFuncDParameters(double x, double y) const
Definition: Function.h:473
Function(std::vector< double > const &params)
Construct a Function given the function parameters.
Definition: Function.h:110
a class used in function calls to indicate that no Function2 is being provided
Definition: Function.h:536
Function2< ReturnT >::Ptr clone() const
Return a pointer to a deep copy of this function.
Definition: Function.h:539
static int orderFromNParameters(int nParameters)
Compute polynomial order from the number of parameters.
Definition: Function.h:454
virtual std::string toString(std::string const &) const
Return a string representation of the function.
Definition: Function.h:192
virtual void computeCache(int const n)
Definition: Function.h:276
ReturnT operator()(double, double) const
Definition: Function.h:543
void serialize(Archive &ar, unsigned const int version)
Definition: Function.h:364
BasePolynomialFunction2(std::vector< double > params)
Construct a polynomial function with specified parameters.
Definition: Function.h:410
A Function taking one argument.
Definition: Function.h:229
Function2(unsigned int nParams)
Construct a Function2 given the number of function parameters.
Definition: Function.h:311
Function1< ReturnT >::Ptr clone() const
Return a pointer to a deep copy of this function.
Definition: Function.h:516
Basic Function class.
Definition: Function.h:89
a class used in function calls to indicate that no Function1 is being provided
Definition: Function.h:513
Function2(std::vector< double > const &params)
Construct a Function2 given the function parameters.
Definition: Function.h:322
ReturnT operator()(double) const
Definition: Function.h:520
int x
virtual ReturnT operator()(double x) const =0
#define LSST_EXCEPT(type,...)
Definition: Exception.h:46
Function1(unsigned int nParams)
Construct a Function1 given the number of function parameters.
Definition: Function.h:240
std::vector< double > _params
Definition: Function.h:204
Citizen(const std::type_info &)
Definition: Citizen.cc:173
void serialize(Archive &ar, unsigned const int version)
Definition: Function.h:501
virtual ReturnT operator()(double x, double y) const =0
Citizen is a class that should be among all LSST classes base classes, and handles basic memory manag...
Definition: Citizen.h:56
void serialize(Archive &ar, unsigned const int version)
Definition: Function.h:286
boost::shared_ptr< Function2< ReturnT > > Ptr
Definition: Function.h:304
virtual bool isLinearCombination() const
Is the function a linear combination of its parameters?
Definition: Function.h:156
friend class boost::serialization::access
Definition: Function.h:546
void serialize(Archive &ar, unsigned int const version)
Definition: Function.h:549
BasePolynomialFunction2(unsigned int order)
Construct a polynomial function of specified order.
Definition: Function.h:395
A CRTP facade class for subclasses of Persistable.
Definition: Persistable.h:182
boost::shared_ptr< Function1< ReturnT > > Ptr
Definition: Function.h:233
void setParameters(std::vector< double > const &params)
Set all function parameters.
Definition: Function.h:175
virtual Ptr clone() const =0
Return a pointer to a deep copy of this function.
Include files required for standard LSST Exception handling.