Xmipp  v3.23.11-Nereus
Functions
UTRSSolver.cpp File Reference
#include <stdio.h>
#include <memory.h>
#include "Matrix.h"
#include "tools.h"
#include "Poly.h"
Include dependency graph for UTRSSolver.cpp:

Go to the source code of this file.

Functions

double findAlpha (Vector s, Vector u, double delta, Polynomial &q, Vector pointXk, Vector &output, Vector minusG, Matrix H)
 
double initLambdaL (double normG, double delta, Matrix H)
 
double initLambdaU (double normG, double delta, Matrix H)
 
double initLambdaU2 (Matrix H)
 
Vector L2NormMinimizer (Polynomial q, Vector pointXk, double delta, int *infoOut, int maxIter, double *lambda1, Vector minusG, Matrix H)
 
Vector L2NormMinimizer (Polynomial q, Vector pointXk, double delta, int *infoOut, int maxIter, double *lambda1)
 
Vector L2NormMinimizer (Polynomial q, double delta, int *infoOut, int maxIter, double *lambda1)
 

Function Documentation

◆ findAlpha()

double findAlpha ( Vector  s,
Vector  u,
double  delta,
Polynomial q,
Vector  pointXk,
Vector output,
Vector  minusG,
Matrix  H 
)

Definition at line 35 of file UTRSSolver.cpp.

39 {
40  static Vector v1, v2, tmp;
41  double a=0,b=0,c=-sqr(delta), *sp=s, *up=u;
42  int n=s.sz();
43  while (n--)
44  {
45  a+=sqr(*up); b+=*up * *sp; c+=sqr(*sp);
46  sp++; up++;
47  }
48  double tmp1=-b/a, tmp2= sqrt(b*b-a*c)/a, q1, q2;
49 
50  n=s.sz();
51  v1.setSize(n); v2.setSize(n); tmp.setSize(n);
53  {
54  v1.copyFrom(u);
55  v1.multiply(tmp1+tmp2);
56  v1+=s;
57  tmp.copyFrom(v1);
58  tmp+=pointXk;
59  q1=q(tmp);
60 
61  // !!! don't do this:
62  // output=v1;
63  // return tmp1+tmp2;
64 
65  v2.copyFrom(u);
66  v2.multiply(tmp1-tmp2);
67  v2+=s;
68  tmp.copyFrom(v2);
69  tmp+=pointXk;
70  q2=q(tmp);
71 
72  } else
73  {
74  v1.copyFrom(u);
75  v1.multiply(tmp1+tmp2);
76  v1+=s;
77  H.multiply(tmp,v1);
78  q1=-minusG.scalarProduct(v1)+0.5*v1.scalarProduct(tmp);
79 
80  v2.copyFrom(u);
81  v2.multiply(tmp1-tmp2);
82  v2+=s;
83  H.multiply(tmp,v2);
84  q2=-minusG.scalarProduct(v2)+0.5*v2.scalarProduct(tmp);
85  }
86  if (q1>q2) { output=v1; return tmp1+tmp2; }
87  output=v2; return tmp1-tmp2;
88 }
doublereal * c
void sqrt(Image< double > &op)
Matrix multiply(Matrix B)
Definition: Matrix.cpp:633
Definition: Vector.h:37
#define q1
void setSize(int _n)
Definition: Vector.cpp:112
unsigned sz()
Definition: Vector.h:79
double sqr(const double &t)
Definition: tools.h:99
doublereal * b
double v1
void multiply(double a)
Definition: Vector.cpp:281
#define q2
double scalarProduct(Vector v)
Definition: Vector.cpp:332
doublereal * u
void copyFrom(Vector r, int _n=0)
Definition: Vector.cpp:215
static Polynomial emptyPolynomial
Definition: Poly.h:126
int * n
doublereal * a
double * delta

◆ initLambdaL()

double initLambdaL ( double  normG,
double  delta,
Matrix  H 
)

Definition at line 90 of file UTRSSolver.cpp.

91 {
92  int n=H.nLine(),i,j;
93  double **h=H, sum,l,a=INF;
94 
95  for (i=0; i<n; i++) a=mmin(a,h[i][i]);
96  l=mmax(0.0,-a);
97 
98  a=0;
99  for (i=0; i<n; i++)
100  {
101  sum=h[i][i];
102  for (j=0; j<n; j++) if (j!=i) sum+=condorAbs(h[i][j]);
103  a=mmax(a,sum);
104  }
105  a=mmin(a,H.frobeniusNorm());
106  a=mmin(a,H.LnftyNorm());
107 
108  l=mmax(l,normG/delta-a);
109  return l;
110 }
double LnftyNorm()
Definition: Matrix.cpp:1058
int * mmax
double mmin(const double t1, const double t2)
Definition: tools.h:69
#define i
int nLine()
Definition: Matrix.h:83
double frobeniusNorm()
Definition: Matrix.cpp:1045
double condorAbs(const double t1)
Definition: tools.h:47
#define j
#define INF
Definition: svm.cpp:43
int * n
doublereal * a
double * delta

◆ initLambdaU()

double initLambdaU ( double  normG,
double  delta,
Matrix  H 
)

Definition at line 112 of file UTRSSolver.cpp.

113 {
114  int n=H.nLine(),i,j;
115  double **h=H, sum,l,a=-INF;
116 
117  for (i=0; i<n; i++)
118  {
119  sum=-h[i][i];
120  for (j=0; j<n; j++) if (j!=i) sum+=condorAbs(h[i][j]);
121  a=mmax(a,sum);
122  }
123  a=mmin(a,H.frobeniusNorm());
124  a=mmin(a,H.LnftyNorm());
125 
126  l=mmax(0.0,normG/delta+a);
127  return l;
128 }
double LnftyNorm()
Definition: Matrix.cpp:1058
int * mmax
double mmin(const double t1, const double t2)
Definition: tools.h:69
#define i
int nLine()
Definition: Matrix.h:83
double frobeniusNorm()
Definition: Matrix.cpp:1045
double condorAbs(const double t1)
Definition: tools.h:47
#define j
#define INF
Definition: svm.cpp:43
int * n
doublereal * a
double * delta

◆ initLambdaU2()

double initLambdaU2 ( Matrix  H)

Definition at line 130 of file UTRSSolver.cpp.

131 {
132  int n=H.nLine(),i,j;
133  double **h=H, sum,a=-INF;
134 
135  for (i=0; i<n; i++)
136  {
137  sum=h[i][i];
138  for (j=0; j<n; j++) if (j!=i) sum+=condorAbs(h[i][j]);
139  a=mmax(a,sum);
140  }
141  a=mmin(a,H.frobeniusNorm());
142  return mmin(a,H.LnftyNorm());
143 }
double LnftyNorm()
Definition: Matrix.cpp:1058
int * mmax
double mmin(const double t1, const double t2)
Definition: tools.h:69
#define i
int nLine()
Definition: Matrix.h:83
double frobeniusNorm()
Definition: Matrix.cpp:1045
double condorAbs(const double t1)
Definition: tools.h:47
#define j
#define INF
Definition: svm.cpp:43
int * n
doublereal * a

◆ L2NormMinimizer() [1/3]

Vector L2NormMinimizer ( Polynomial  q,
Vector  pointXk,
double  delta,
int *  infoOut,
int  maxIter,
double *  lambda1,
Vector  minusG,
Matrix  H 
)

Definition at line 147 of file UTRSSolver.cpp.

149 {
150 // lambda1>0.0 if interior convergence
151 
152  const double theta=0.01;
153 // const double kappaEasy=0.1, kappaHard=0.2;
154  const double kappaEasy=0.01, kappaHard=0.02;
155 
156  double normG,lambda,lambdaCorrection, lambdaPlus, lambdaL, lambdaU,
157  uHu, alpha, normS;
158  int info=0, n=minusG.sz();
159  Matrix HLambda(n,n);
160  MatrixTriangle L(n);
161  Vector s(n), omega(n), u(n), sFinal;
162  bool gIsNull, choleskyFactorAlreadyComputed=false;
163 
164 // printf("\nG= "); minusG.print();
165 // printf("\nH=\n"); H.print();
166 
167  gIsNull=minusG.isNull();
168  normG=minusG.euclidianNorm();
169  lambda=normG/delta;
170  minusG.multiply(-1.0);
171 
172  lambdaL=initLambdaL(normG,delta,H);
173  lambdaU=initLambdaU(normG,delta,H);
174 
175  // Special case: parl = paru.
176  lambdaU= mmax(lambdaU,(1+kappaEasy)*lambdaL);
177 
178  lambda=mmax(lambda, lambdaL);
179  lambda=mmin(lambda, lambdaU);
180 
181  while (maxIter--)
182  {
183  if (!choleskyFactorAlreadyComputed)
184  {
185  if (!H.cholesky(L, lambda, &lambdaCorrection))
186  {
187  // lambdaL=mmax(mmax(lambdaL,lambda),lambdaCorrection);
188  lambdaL=mmax(lambdaL,lambda+lambdaCorrection);
189  lambda=mmax(sqrt(lambdaL*lambdaU), lambdaL+theta*(lambdaU-lambdaL));
190  continue;
191  }
192  } else choleskyFactorAlreadyComputed=false;
193 
194 
195  // cholesky factorization successful : solve Hlambda * s = -G
196  s.copyFrom(minusG);
197  L.solveInPlace(s);
198  L.solveTransposInPlace(s);
199  normS=s.euclidianNorm();
200 
201  // check for termination
202 #ifndef POWEL_TERMINATION
203  if (condorAbs(normS-delta)<kappaEasy*delta)
204  {
205  s.multiply(delta/normS);
206  info=1;
207  break;
208  }
209 #else
210 // powell check !!!
211  HLambda.copyFrom(H);
212  HLambda.addUnityInPlace(lambda);
213  double sHs=s.scalarProduct(HLambda.multiply(s));
214  if (sqr(delta/normS-1)<kappaEasy*(1+lambda*delta*delta/sHs))
215  {
216  s.multiply(delta/normS);
217  info=1;
218  break;
219  }
220 #endif
221 
222  if (normS<delta)
223  {
224  // check for termination
225  // interior convergence; maybe break;
226  if (lambda==0) { info=1; break; }
227  lambdaU=mmin(lambdaU,lambda);
228  } else lambdaL=mmax(lambdaL,lambda);
229 
230 // if (lambdaU-lambdaL<kappaEasy*(2-kappaEasy)*lambdaL) { info=3; break; };
231 
232  omega.copyFrom(s);
233  L.solveInPlace(omega);
234  lambdaPlus=lambda+(normS-delta)/delta*sqr(normS)/sqr(omega.euclidianNorm());
235  lambdaPlus=mmax(lambdaPlus, lambdaL);
236  lambdaPlus=mmin(lambdaPlus, lambdaU);
237 
238  if (normS<delta)
239  {
240  L.LINPACK(u);
241 #ifndef POWEL_TERMINATION
242  HLambda.copyFrom(H);
243  HLambda.addUnityInPlace(lambda);
244 #endif
245  uHu=u.scalarProduct(HLambda.multiply(u));
246  lambdaL=mmax(lambdaL,lambda-uHu);
247 
248  alpha=findAlpha(s,u,delta,q,pointXk,sFinal,minusG,H);
249  // check for termination
250 #ifndef POWEL_TERMINATION
251  if (sqr(alpha)*uHu<
252  kappaHard*(s.scalarProduct(HLambda.multiply(s)) ))// +lambda*sqr(delta)))
253 #else
254  if (sqr(alpha)*uHu+sHs<
255  kappaHard*(sHs+lambda*sqr(delta)))
256 #endif
257  {
258  s=sFinal; info=2; break;
259  }
260  }
261  if ((normS>delta)&&(!gIsNull)) { lambda=lambdaPlus; continue; };
262 
263  if (H.cholesky(L, lambdaPlus, &lambdaCorrection))
264  {
265  lambda=lambdaPlus;
266  choleskyFactorAlreadyComputed=true;
267  continue;
268  }
269 
270  lambdaL=mmax(lambdaL,lambdaPlus);
271  // check lambdaL for interior convergence
272 // if (lambdaL==0) return s;
273  lambda=mmax(sqrt(lambdaL*lambdaU), lambdaL+theta*(lambdaU-lambdaL));
274  }
275 
276  if (infoOut) *infoOut=info;
277  if (lambda1)
278  {
279  if (lambda==0.0)
280  {
281  // calculate the value of the lowest eigenvalue of H
282  // to check
283  lambdaL=0; lambdaU=initLambdaU2(H);
284  while (lambdaL<0.99*lambdaU)
285  {
286  lambda=0.5*(lambdaL+lambdaU);
287  if (H.cholesky(L,-lambda)) lambdaL=lambda;
288 // if (H.cholesky(L,-lambda,&lambdaCorrection)) lambdaL=lambda+lambdaCorrection;
289  else lambdaU=lambda;
290  }
291  *lambda1=lambdaL;
292  } else *lambda1=0.0;
293  }
294  return s;
295 }
double initLambdaL(double normG, double delta, Matrix H)
Definition: UTRSSolver.cpp:90
int * mmax
double initLambdaU2(Matrix H)
Definition: UTRSSolver.cpp:130
void sqrt(Image< double > &op)
Definition: Vector.h:37
double euclidianNorm()
Definition: Vector.cpp:222
double mmin(const double t1, const double t2)
Definition: tools.h:69
double initLambdaU(double normG, double delta, Matrix H)
Definition: UTRSSolver.cpp:112
double theta
unsigned sz()
Definition: Vector.h:79
double sqr(const double &t)
Definition: tools.h:99
bool cholesky(MatrixTriangle matL, double lambda=0, double *lambdaCorrection=NULL)
Definition: Matrix.cpp:763
double * lambda
double condorAbs(const double t1)
Definition: tools.h:47
Definition: Matrix.h:38
void multiply(double a)
Definition: Vector.cpp:281
bool isNull()
Definition: Vector.cpp:358
doublereal * u
double findAlpha(Vector s, Vector u, double delta, Polynomial &q, Vector pointXk, Vector &output, Vector minusG, Matrix H)
Definition: UTRSSolver.cpp:35
int * n
double * delta

◆ L2NormMinimizer() [2/3]

Vector L2NormMinimizer ( Polynomial  q,
Vector  pointXk,
double  delta,
int *  infoOut,
int  maxIter,
double *  lambda1 
)

Definition at line 297 of file UTRSSolver.cpp.

299 {
300  int n=q.dim();
301  Matrix H(n,n);
302  Vector vG(n);
303  q.gradientHessian(pointXk,vG,H);
304  return L2NormMinimizer(q,pointXk,delta,infoOut,maxIter,lambda1,vG,H);
305 }
Vector L2NormMinimizer(Polynomial q, Vector pointXk, double delta, int *infoOut, int maxIter, double *lambda1, Vector minusG, Matrix H)
Definition: UTRSSolver.cpp:147
Definition: Vector.h:37
unsigned dim()
Definition: Poly.h:62
void gradientHessian(Vector P, Vector G, Matrix H)
Definition: Poly.cpp:515
Definition: Matrix.h:38
int * n
double * delta

◆ L2NormMinimizer() [3/3]

Vector L2NormMinimizer ( Polynomial  q,
double  delta,
int *  infoOut,
int  maxIter,
double *  lambda1 
)

Definition at line 307 of file UTRSSolver.cpp.

309 {
310  return L2NormMinimizer(q, Vector::emptyVector, delta, infoOut, maxIter, lambda1);
311 }
Vector L2NormMinimizer(Polynomial q, Vector pointXk, double delta, int *infoOut, int maxIter, double *lambda1, Vector minusG, Matrix H)
Definition: UTRSSolver.cpp:147
static Vector emptyVector
Definition: Vector.h:119
double * delta