cvLevenbergMarquardtOptimizationで最小化
void cvLevenbergMarquardtOptimization(pointer_LMJac JacobianFunction, pointer_LMFunc function, CvMat *X0, CvMat *observRes, CvMat *resultX, int maxIter, double epsilon);
な,長い・・・
#geshi(c++,number){{
//cvaux/src/cvlevmartif.cppにTriFocalを求める過程でLevenbergMarqurdtが求められている.
#include <cvlevmar.cpp>
#include <cv.h>
#include <cvaux.h>
#include <cxcore.h>
#include <highgui.h>
#include <stdio.h>
#include <math.h>
#define A 100
#define B 102
#define PRECISION 100
#define DERIV_STEP 0.00001
void CalcDiff( const CvMat *src, CvMat *dst);
void CalcDerivDiff( const CvMat *src, CvMat *dst);
double coreCalculation( const CvMat *src, double x);
int main(){
CvMat *src, *dst, *X0, *res;
FILE *fp = fopen("./data", "w");
fclose(fp);
X0 = cvCreateMat(2, 1, CV_64F);
src = cvCreateMat(2, 1, CV_64F);
dst = cvCreateMat(PRECISION, 1, CV_64F);
res = cvCreateMat(X0->rows, X0->cols, CV_64F);
cvmSet(X0, 0, 0, 100);
cvmSet(X0, 1, 0, 102);
CalcDiff(X0, dst);
cvmSet(X0, 0, 0, 0);
cvmSet(X0, 1, 0, 0);
cvLevenbergMarquardtOptimization((pointer_LMJac)CalcDerivDiff, (pointer_LMFunc)CalcDiff, X0, dst, res, 50, 0.01);
return 0;
}
void CalcDiff( const CvMat *src, CvMat *dst){
int i;
double x, val;
FILE *fp = fopen("./data", "a");
static count = 0;
printf("%d repeat\n", count++);
for(i = 0;i < PRECISION;i++){
x = CV_PI * ((double)i / PRECISION);
val = coreCalculation(src, x);
cvmSet(dst, i, 0, val);
fprintf(fp, "%f\t", cvmGet(dst, i, 0));
}
fprintf(fp, "\n");
}
void CalcDerivDiff( const CvMat *src, CvMat *dst){
int i, j;
double x, val, nextval;
CvMat *next = cvCreateMat(src->rows,src->cols,src->type);
for(j = 0;j < 2;j++){
cvCopy( src, next);
cvmSet(next, j, 0, cvmGet(src, j, 0) + DERIV_STEP);
for(i = 0;i < PRECISION;i++){
x = CV_PI * ((double)i / PRECISION);
val = coreCalculation(src, x);
nextval = coreCalculation(next, x);
cvmSet(dst, i, j, nextval - val);
}
}
}
double coreCalculation( const CvMat *src, double x){
double a = cvmGet(src, 0, 0);
double b = cvmGet(src, 1, 0);
//return a*cos(b*x) + b*sin(a*x);
return a*cos(3*x) + b*sin(60*x);
}
}}