Logo ROOT   6.30.04
Reference Guide
 All Namespaces Files Pages
MinimTransformFunction.cxx
Go to the documentation of this file.
1 // @(#)root/mathmore:$Id$
2 // Author: L. Moneta June 2009
3 
4 /**********************************************************************
5  * *
6  * Copyright (c) 2006 LCG ROOT Math Team, CERN/PH-SFT *
7  * *
8  * *
9  **********************************************************************/
10 
11 // Implementation file for class MinimTransformFunction
12 
14 #include "Math/IFunctionfwd.h"
15 
16 //#include <iostream>
17 #include <cmath>
18 #include <cassert>
19 
20 namespace ROOT {
21 
22  namespace Math {
23 
24 MinimTransformFunction::MinimTransformFunction ( const IMultiGradFunction * f, const std::vector<EMinimVariableType> & types,
25  const std::vector<double> & values,
26  const std::map<unsigned int, std::pair<double, double> > & bounds) :
27  fX( values ),
28  fFunc(f)
29 {
30  // constructor of the class from a pointer to the function (which is managed)
31  // vector specifying the variable types (free, bounded or fixed, defined in enum EMinimVariableTypes )
32  // variable values (used for the fixed ones) and a map with the bounds (for the bounded variables)
33 
34  unsigned int ntot = NTot(); // NTot is fFunc->NDim()
35  assert ( types.size() == ntot );
36  fVariables.reserve(ntot);
37  fIndex.reserve(ntot);
38  for (unsigned int i = 0; i < ntot; ++i ) {
39  if (types[i] == kFix )
40  fVariables.push_back( MinimTransformVariable( values[i]) );
41  else {
42  fIndex.push_back(i);
43 
44  if ( types[i] == kDefault)
45  fVariables.push_back( MinimTransformVariable() );
46  else {
47  std::map<unsigned int, std::pair<double,double> >::const_iterator itr = bounds.find(i);
48  assert ( itr != bounds.end() );
49  double low = itr->second.first;
50  double up = itr->second.second;
51  if (types[i] == kBounds )
52  fVariables.push_back( MinimTransformVariable( low, up, new SinVariableTransformation()));
53  else if (types[i] == kLowBound)
54  fVariables.push_back( MinimTransformVariable( low, new SqrtLowVariableTransformation()));
55  else if (types[i] == kUpBound)
56  fVariables.push_back( MinimTransformVariable( up, new SqrtUpVariableTransformation()));
57  }
58  }
59  }
60 }
61 
62 
63 void MinimTransformFunction::Transformation( const double * x, double * xext) const {
64  // transform from internal to external
65 
66  unsigned int nfree = fIndex.size();
67 
68 // std::cout << "Transform: internal ";
69 // for (int i = 0; i < nfree; ++i) std::cout << x[i] << " ";
70 // std::cout << "\t\t";
71 
72  for (unsigned int i = 0; i < nfree; ++i ) {
73  unsigned int extIndex = fIndex[i];
74  const MinimTransformVariable & var = fVariables[ extIndex ];
75  if (var.IsLimited() )
76  xext[ extIndex ] = var.InternalToExternal( x[i] );
77  else
78  xext[ extIndex ] = x[i];
79  }
80 
81 // std::cout << "Transform: external ";
82 // for (int i = 0; i < fX.size(); ++i) std::cout << fX[i] << " ";
83 // std::cout << "\n";
84 
85 }
86 
87 void MinimTransformFunction::InvTransformation(const double * xExt, double * xInt) const {
88  // inverse function transformation (external -> internal)
89  for (unsigned int i = 0; i < NDim(); ++i ) {
90  unsigned int extIndex = fIndex[i];
91  const MinimTransformVariable & var = fVariables[ extIndex ];
92  assert ( !var.IsFixed() );
93  if (var.IsLimited() )
94  xInt[ i ] = var.ExternalToInternal( xExt[extIndex] );
95  else
96  xInt[ i ] = xExt[extIndex];
97  }
98 }
99 
100 void MinimTransformFunction::InvStepTransformation(const double * x, const double * sExt, double * sInt) const {
101  // inverse function transformation for steps (external -> internal)
102  for (unsigned int i = 0; i < NDim(); ++i ) {
103  unsigned int extIndex = fIndex[i];
104  const MinimTransformVariable & var = fVariables[ extIndex ];
105  assert ( !var.IsFixed() );
106  if (var.IsLimited() ) {
107  // bound variables
108  double x2 = x[extIndex] + sExt[extIndex];
109  if (var.HasUpperBound() && x2 >= var.UpperBound() )
110  x2 = x[extIndex] - sExt[extIndex];
111  // transform x and x2
112  double xint = var.ExternalToInternal ( x[extIndex] );
113  double x2int = var.ExternalToInternal( x2 );
114  sInt[i] = std::abs( x2int - xint);
115  }
116  else
117  sInt[ i ] = sExt[extIndex];
118  }
119 }
120 
121 void MinimTransformFunction::GradientTransformation(const double * x, const double *gExt, double * gInt) const {
122  //transform gradient vector (external -> internal) at internal point x
123  unsigned int nfree = fIndex.size();
124  for (unsigned int i = 0; i < nfree; ++i ) {
125  unsigned int extIndex = fIndex[i];
126  const MinimTransformVariable & var = fVariables[ extIndex ];
127  assert (!var.IsFixed() );
128  if (var.IsLimited() )
129  gInt[i] = gExt[ extIndex ] * var.DerivativeIntToExt( x[i] );
130  else
131  gInt[i] = gExt[ extIndex ];
132  }
133 }
134 
135 
136 void MinimTransformFunction::MatrixTransformation(const double * x, const double *covInt, double * covExt) const {
137  //transform covariance matrix (internal -> external) at internal point x
138  // use row storages for matrices m(i,j) = rep[ i * dim + j]
139  // ignore fixed points
140  unsigned int nfree = fIndex.size();
141  unsigned int ntot = NTot();
142  for (unsigned int i = 0; i < nfree; ++i ) {
143  unsigned int iext = fIndex[i];
144  const MinimTransformVariable & ivar = fVariables[ iext ];
145  assert (!ivar.IsFixed());
146  double ddi = ( ivar.IsLimited() ) ? ivar.DerivativeIntToExt( x[i] ) : 1.0;
147  // loop on j variables for not fixed i variables (forget that matrix is symmetric) - could be optimized
148  for (unsigned int j = 0; j < nfree; ++j ) {
149  unsigned int jext = fIndex[j];
150  const MinimTransformVariable & jvar = fVariables[ jext ];
151  double ddj = ( jvar.IsLimited() ) ? jvar.DerivativeIntToExt( x[j] ) : 1.0;
152  assert (!jvar.IsFixed() );
153  covExt[ iext * ntot + jext] = ddi * ddj * covInt[ i * nfree + j];
154  }
155  }
156 }
157 
158 
159  } // end namespace Math
160 
161 } // end namespace ROOT
162