ccgsl 2.7.2
C++wrappersforGnuScientificLibrary
multifit_nlinear.hpp
Go to the documentation of this file.
1/*
2 * $Id$
3 * Copyright (C) 2020 John D Lamb
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or (at
8 * your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
18 */
19
20#ifndef CCGSL_MULTIFIT_NLINEAR_HPP
21#define CCGSL_MULTIFIT_NLINEAR_HPP
22
23#include<cmath>
24#include<gsl/gsl_multifit_nlinear.h>
25#include"vector.hpp"
26#include"matrix.hpp"
28
29namespace gsl {
34 namespace multifit {
38 namespace nlinear {
42 class workspace {
43 public:
48 ccgsl_pointer = 0;
49 count = 0; // initially nullptr will do
50 }
51 // Refines random access container
52 // Refines assignable
60 explicit workspace( gsl_multifit_nlinear_type const* T,
61 gsl_multifit_nlinear_parameters const* params,
62 size_t const n, size_t const p ){
63 ccgsl_pointer = gsl_multifit_nlinear_alloc( T, params, n, p );
64 // just plausibly we could allocate workspace but not count
65 try { count = new size_t; } catch( std::bad_alloc& e ){
66 // try to tidy up before rethrowing
67 gsl_multifit_nlinear_free( ccgsl_pointer );
68 throw e;
69 }
70 *count = 1; // initially there is just one reference to ccgsl_pointer
71 }
79 explicit workspace( gsl_multifit_nlinear_workspace* v ){
80 ccgsl_pointer = v;
81 // just plausibly we could fail to allocate count: no further action needed.
82 count = new size_t;
83 *count = 1;
84 // initially there is just one reference to ccgsl_pointer
85 }
86 // copy constructor
92 count = v.count; if( count != 0 ) ++*count; }
93 // assignment operator
99 // first, possibly delete anything pointed to by this
100 if( count == 0 or --*count == 0 ){
101 if( ccgsl_pointer != 0 ) gsl_multifit_nlinear_free( ccgsl_pointer );
102 delete count;
103 } // Then copy
104 ccgsl_pointer = v.ccgsl_pointer; count = v.count; if( count != 0 ) ++*count;
105 return *this;
106 }
107 // destructor
112 if( count == 0 or --*count == 0 ){
113 // could have allocated null pointer
114 if( ccgsl_pointer != 0 ) gsl_multifit_nlinear_free( ccgsl_pointer );
115 delete count;
116 }
117 }
118#ifdef __GXX_EXPERIMENTAL_CXX0X__
124 : ccgsl_pointer( v.ccgsl_pointer ), count( nullptr ){
125 std::swap( count, v.count );
126 v.ccgsl_pointer = nullptr;
127 }
134 workspace( std::move( v ) ).swap( *this );
135 return *this;
136 }
137#endif
138 // Allow possibility of assigning from gsl_multifit_nlinear_workspace without sharing
149 ( gsl_multifit_nlinear_workspace* w ){
150 if( count != 0 and --*count == 0 ){
151 // could have allocated null pointer
152 if( ccgsl_pointer != 0 ) gsl_multifit_nlinear_free( ccgsl_pointer );
153 }
154 ccgsl_pointer = w;
155 if(0 == count) count = new size_t;
156 *count = 2; // should never be able to delete ccgsl_pointer
157 }
158 // Refines equality comparable
159 // == operator
166 bool operator==( workspace const& v ) const { return ccgsl_pointer == v.ccgsl_pointer; }
167 // != operator
174 bool operator!=( workspace const& v ) const { return not operator==( v ); }
175 // Refines forward container
176 // Refines less than comparable
177 // operator<
186 bool operator<( workspace const& v ) const { return ccgsl_pointer < v.ccgsl_pointer; }
187 // operator>
196 bool operator>( workspace const& v ) const { return ccgsl_pointer > v.ccgsl_pointer; }
197 // operator<=
206 bool operator<=( workspace const& v ) const { return ccgsl_pointer <= v.ccgsl_pointer; }
207 // operator>=
216 bool operator>=( workspace const& v ) const { return ccgsl_pointer >= v.ccgsl_pointer; }
221 bool empty() const { return ccgsl_pointer == 0; }
222 // swap() --- should work even if sizes don't match
228 void swap( workspace& v ){
229 std::swap( ccgsl_pointer, v.ccgsl_pointer );
230 std::swap( count, v.count );
231 }
232 private:
236 gsl_multifit_nlinear_workspace* ccgsl_pointer;
240 size_t* count;
241 public:
242 // shared reference functions
247 gsl_multifit_nlinear_workspace* get() const { return ccgsl_pointer; }
253 bool unique() const { return count != 0 and *count == 1; }
258 size_t use_count() const { return count == 0 ? 0 : *count; }
264#ifdef __GXX_EXPERIMENTAL_CXX0X__
265 explicit
266#endif
267 operator bool() const { return ccgsl_pointer != 0; }
268 };
281 public:
287 virtual void function( size_t const iter, workspace const& w ) = 0;
288 };
289#ifndef DOXYGEN_SKIP
293 class CallbackImplement {
294 public:
298 typedef void (*function_t)(size_t const,void*,gsl_multifit_nlinear_workspace const*);
302 class base_F {
303 public:
307 virtual ~base_F(){}
312 virtual function_t getFunction() = 0;
313 };
317 template<typename T> class F : public base_F {
318 public:
322 F(){}
329 static void function( size_t const i, void* params,
330 gsl_multifit_nlinear_workspace const* w ){
331 T* t = reinterpret_cast<T*>( params );
332 workspace W;
333 W.wrap_gsl_multifit_nlinear_workspace_without_ownership
334 ( const_cast<gsl_multifit_nlinear_workspace*>( w ) );
335 return t->function( i, W );
336 }
341 function_t getFunction(){ return &F<T>::function; }
342 };
347 template<typename T> CallbackImplement( T& t ){
348 f = new F<T>;
349 // just plausibly we could fail to allocate count: no further action needed.
350 count = new size_t;
351 *count = 1; // initially there is just one reference to f
352 }
353 // Copy and move constructors
354 // copy constructor
359 CallbackImplement( CallbackImplement const& v ) : f( v.f ), count( v.count ){
360 if( count != 0 ) ++*count; // CallbackImplementation is now shared.
361 }
362 // assignment operator
367 CallbackImplement& operator=( CallbackImplement const& v ){
368 // first, possibly delete anything pointed to by this
369 if( count == 0 or --*count == 0 ){
370 delete f;
371 delete count;
372 }
373 // Then copy
374 f = v.f;
375 count = v.count;
376 if( count != 0 ) ++*count; // CallbackImplement object is now shared.
377 return *this;
378 }
379#ifdef __GXX_EXPERIMENTAL_CXX0X__
384 CallbackImplement( CallbackImplement&& v ) : f( v.f ), count( nullptr ){
385 std::swap( count, v.count );
386 v.f = nullptr;
387 }
393 CallbackImplement& operator=( CallbackImplement&& v ){
394 std::swap( f, v.f );
395 std::swap( count, v.count );
396 return *this;
397 }
398#endif
402 ~CallbackImplement(){
403 // first, possibly delete anything pointed to by f
404 if( count == 0 or --*count == 0 ){
405 delete f;
406 delete count;
407 }
408 }
413 function_t getFunction(){ return f->getFunction(); }
414 private:
418 base_F* f;
422 size_t* count;
423 };
424#endif
429 inline gsl_multifit_nlinear_parameters
430 default_parameters(){ return gsl_multifit_nlinear_default_parameters(); }
439 inline int
441 workspace& w ){
442 return gsl_multifit_nlinear_init( x.get(), &fdf, w.get() ); }
451 inline int
452 winit( vector const& x, vector const& wts,
454 return gsl_multifit_nlinear_winit( x.get(), wts.get(), &fdf, w.get() ); }
460 inline int
461 iterate( workspace& w ){ return gsl_multifit_nlinear_iterate( w.get() ); }
467 inline double
468 avratio( workspace const& w ){ return gsl_multifit_nlinear_avratio( w.get() ); }
481 inline int
482 driver( size_t const maxiter,
483 double const xtol,
484 double const gtol,
485 double const ftol,
486 CallbackBase& callback,
487 int& info, workspace& w ){
488 void* callback_params = reinterpret_cast<void*>( &callback );
489 CallbackImplement callbackImplement( callback );
490 void (*function)(size_t const,void*,gsl_multifit_nlinear_workspace const*)
491 = callbackImplement.getFunction();
492 return gsl_multifit_nlinear_driver( maxiter, xtol, gtol, ftol, function,
493 callback_params, &info, w.get() ); }
497 typedef void (*driver_callback)(const size_t iter, void* params,
498 gsl_multifit_nlinear_workspace const* w);
511 inline int
512 driver( size_t const maxiter,
513 double const xtol,
514 double const gtol,
515 double const ftol,
516 driver_callback callback,
517 void* callback_params,
518 int* info, workspace& w ){
519 return gsl_multifit_nlinear_driver( maxiter, xtol, gtol, ftol,
520 callback,
521 callback_params, info, w.get() ); }
527 inline matrix
528 jac( workspace const& w ){
530 result.wrap_gsl_matrix_without_ownership( gsl_multifit_nlinear_jac( w.get() ) );
531 return result; }
537 inline char const*
538 name( workspace const& w ){ return gsl_multifit_nlinear_name( w.get() ); }
544 inline vector
545 position( workspace const& w ){
547 result.wrap_gsl_vector_without_ownership( gsl_multifit_nlinear_position( w.get() ) );
548 return result; }
554 inline vector
555 residual( workspace const& w ){
557 result.wrap_gsl_vector_without_ownership( gsl_multifit_nlinear_residual( w.get() ) );
558 return result; }
564 inline size_t
565 niter( workspace const& w ){ return gsl_multifit_nlinear_niter( w.get() ); }
572 inline int
573 rcond( double& rcond, workspace const& w ){
574 return gsl_multifit_nlinear_rcond( &rcond, w.get() ); }
581 inline int
582 rcond( double* rcond, workspace const& w ){
583 return gsl_multifit_nlinear_rcond( rcond, w.get() ); }
589 inline char const*
590 trs_name( workspace const& w ){
591 return gsl_multifit_nlinear_trs_name( w.get() ); }
600 inline int
602 vector const& swts, vector& y ){
603 return gsl_multifit_nlinear_eval_f( &fdf, x.get(), swts.get(), y.get() ); }
616 inline int
617 eval_df( vector const& x, vector const& f, vector const& swts, double const h,
618 gsl_multifit_nlinear_fdtype const fdtype,
620 matrix& df, vector& work ){
621 return gsl_multifit_nlinear_eval_df( x.get(), f.get(), swts.get(), h,
622 fdtype, &fdf, df.get(), work.get() ); }
636 inline int
637 eval_fvv( double const h, vector const& x, vector const& v, vector const& f,
638 matrix const& J, vector const& swts,
640 vector& yvv, vector& work ){
641 return gsl_multifit_nlinear_eval_fvv( h, x.get(), v.get(), f.get(),
642 J.get(), swts.get(), &fdf,
643 yvv.get(), work.get() ); }
651 inline int
652 covar( matrix const& J,
653 double const epsrel,
654 matrix& covar ){
655 return gsl_multifit_nlinear_covar( J.get(), epsrel, covar.get() ); }
665 inline int
666 test( double const xtol, double const gtol, double const ftol, int* info,
667 workspace const& w ){
668 return gsl_multifit_nlinear_test( xtol, gtol, ftol, info, w.get() ); }
678 inline int
679 test( double const xtol, double const gtol, double const ftol, int& info,
680 workspace const& w ){
681 return gsl_multifit_nlinear_test( xtol, gtol, ftol, &info, w.get() ); }
694 inline int
695 df( double const h, gsl_multifit_nlinear_fdtype const fdtype,
696 vector const& x, vector const& wts,
698 vector const& f, matrix& J, vector& work ){
699 return gsl_multifit_nlinear_df( h, fdtype, x.get(), wts.get(), &fdf,
700 f.get(), J.get(), work.get() ); }
714 inline int
715 fdfvv( double const h, vector const& x, vector const& v, vector const& f,
716 matrix const& J, vector const& swts,
718 vector& fvv, vector& work ){
719 return gsl_multifit_nlinear_fdfvv( h, x.get(), v.get(), f.get(), J.get(),
720 swts.get(), &fdf, fvv.get(),
721 work.get() ); }
722 }
723
724 }
725}
726#endif
This class handles matrix objects as shared handles.
Definition: matrix.hpp:72
gsl_matrix * get()
Get the gsl_matrix.
Definition: matrix.hpp:1207
Class that extends gsl_multifit_function so that it can be constructed from arbitrary function object...
You can create callbacks as a subclass of this class.
virtual void function(size_t const iter, workspace const &w)=0
This is the callback function.
Class that extends gsl_multifit_nlinear_fdf so that it can be constructed from arbitrary function obj...
Workspace for nonlinear linear least squares fitting.
workspace(workspace &&v)
Move constructor.
~workspace()
The destructor only deletes the pointers if count reaches zero.
bool operator>(workspace const &v) const
A container needs to define an ordering for sorting.
gsl_multifit_nlinear_workspace * ccgsl_pointer
The shared pointer.
workspace(gsl_multifit_nlinear_workspace *v)
Could construct from a gsl_multifit_workspace.
size_t use_count() const
Find how many workspace objects share this pointer.
bool operator!=(workspace const &v) const
Two workspace are different if their elements are not identical.
bool operator<=(workspace const &v) const
A container needs to define an ordering for sorting.
workspace()
The default constructor is only really useful for assigning to.
void wrap_gsl_multifit_nlinear_workspace_without_ownership(gsl_multifit_nlinear_workspace *w)
This function is intended mainly for internal use.
workspace(gsl_multifit_nlinear_type const *T, gsl_multifit_nlinear_parameters const *params, size_t const n, size_t const p)
The default constructor creates a new workspace with n elements.
workspace & operator=(workspace const &v)
The assignment operator.
workspace(workspace const &v)
The copy constructor.
bool unique() const
Find if this is the only object sharing the gsl_multifit_nlinear_workspace.
bool empty() const
Find if the workspace is empty.
size_t * count
The shared reference count.
bool operator>=(workspace const &v) const
A container needs to define an ordering for sorting.
gsl_multifit_nlinear_workspace * get() const
Get the gsl_multifit_nlinear_workspace.
workspace & operator=(workspace &&v)
Move operator.
bool operator==(workspace const &v) const
Two workspace are identically equal if their elements are identical.
bool operator<(workspace const &v) const
A container needs to define an ordering for sorting.
void swap(workspace &v)
Swap two workspace objects.
This class handles vector objects as shared handles.
Definition: vector.hpp:74
gsl_vector * get()
Get the gsl_vector.
Definition: vector.hpp:1320
int test(double const xtol, double const gtol, double const ftol, int *info, workspace const &w)
C++ version of gsl_multifit_nlinear_test().
int eval_f(gsl::multifit::nlinear::function_fdf &fdf, vector const &x, vector const &swts, vector &y)
C++ version of gsl_multifit_nlinear_eval_f().
char const * name(workspace const &w)
C++ version of gsl_multifit_nlinear_name().
int eval_fvv(double const h, vector const &x, vector const &v, vector const &f, matrix const &J, vector const &swts, gsl::multifit::nlinear::function_fdf &fdf, vector &yvv, vector &work)
C++ version of gsl_multifit_nlinear_eval_fvv().
gsl_multifit_nlinear_parameters default_parameters()
C++ version of gsl_multifit_nlinear_default_parameters().
int iterate(workspace &w)
C++ version of gsl_multifit_nlinear_iterate().
char const * trs_name(workspace const &w)
C++ version of gsl_multifit_nlinear_trs_name().
double avratio(workspace const &w)
C++ version of gsl_multifit_nlinear_avratio().
vector position(workspace const &w)
C++ version of gsl_multifit_nlinear_position().
int init(vector const &x, gsl::multifit::nlinear::function_fdf &fdf, workspace &w)
C++ version of gsl_multifit_nlinear_init().
int covar(matrix const &J, double const epsrel, matrix &covar)
C++ version of gsl_multifit_nlinear_covar().
int driver(size_t const maxiter, double const xtol, double const gtol, double const ftol, CallbackBase &callback, int &info, workspace &w)
C++ version of gsl_multifit_nlinear_driver().
int winit(vector const &x, vector const &wts, gsl::multifit::nlinear::function_fdf &fdf, workspace &w)
C++ version of gsl_multifit_nlinear_winit().
void(* driver_callback)(const size_t iter, void *params, gsl_multifit_nlinear_workspace const *w)
Function pointer for use by driver.
int df(double const h, gsl_multifit_nlinear_fdtype const fdtype, vector const &x, vector const &wts, gsl::multifit::nlinear::function_fdf &fdf, vector const &f, matrix &J, vector &work)
C++ version of gsl_multifit_nlinear_df().
int rcond(double &rcond, workspace const &w)
C++ version of gsl_multifit_nlinear_rcond().
int fdfvv(double const h, vector const &x, vector const &v, vector const &f, matrix const &J, vector const &swts, gsl::multifit::nlinear::function_fdf &fdf, vector &fvv, vector &work)
C++ version of gsl_multifit_nlinear_fdfvv().
matrix jac(workspace const &w)
C++ version of gsl_multifit_nlinear_jac().
vector residual(workspace const &w)
C++ version of gsl_multifit_nlinear_residual().
int eval_df(vector const &x, vector const &f, vector const &swts, double const h, gsl_multifit_nlinear_fdtype const fdtype, gsl::multifit::nlinear::function_fdf &fdf, matrix &df, vector &work)
C++ version of gsl_multifit_nlinear_eval_df().
size_t niter(workspace const &w)
C++ version of gsl_multifit_nlinear_niter().
gsl_multilarge_nlinear_fdf fdf
Typedef for shorthand.
gsl_multilarge_nlinear_fdtype fdtype
Typedef for shorthand.
size_t n(workspace const &w)
C++ version of gsl_rstat_n().
Definition: rstat.hpp:299
double F(double phi, double k, mode_t mode)
C++ version of gsl_sf_ellint_F().
Definition: sf_ellint.hpp:138
gsl_sf_result result
Typedef for gsl_sf_result.
Definition: sf_result.hpp:30
The gsl package creates an interface to the GNU Scientific Library for C++.
Definition: blas.hpp:34