Я пытаюсь использовать hipparchus.org/hipparchus-optim/leastsquares.html, чтобы найти неизвестные A, B, C, D, E, F для преобразования координат, определяемого уравнениями:
x' = Ax + By + C
y' = Dx + Ey + F
Где (x',y') — это точки эталонного изображения, а (x,y) — соответствующие точки на целевом изображении, которые необходимо масштабировать, вращать и переводить в соответствии с эталонным изображением.
Я попробовал следующий код , но не может вычислить правильные результаты.
import org.hipparchus.geometry.euclidean.twod.Vector2D;
import org.hipparchus.linear.Array2DRowRealMatrix;
import org.hipparchus.linear.ArrayRealVector;
import org.hipparchus.linear.RealMatrix;
import org.hipparchus.linear.RealVector;
import org.hipparchus.optim.nonlinear.vector.leastsquares.*;
import org.hipparchus.util.Pair;
/**
* Determine scale, rotation and translation needed to transform the
* target image to match the reference image.
* To do this we need to solve:
* x' = Ax + By + C
* y' = Dx + Ey + F
* (x, y ) are from the target frame,
* (x',y') are from the reference
*/
public class TransformSolver {
final Vector2D[] refPoints;
final Vector2D[] tgtPoints;
MultivariateJacobianFunction model = new MultivariateJacobianFunction() {
public Pair value(final RealVector constants) {
RealVector value = new ArrayRealVector(tgtPoints.length);
RealMatrix jacobian = new Array2DRowRealMatrix(tgtPoints.length, 3);
double A = constants.getEntry(0);
double B = constants.getEntry(1);
double C = constants.getEntry(2);
for (int i = 0; i < tgtPoints.length; ++i) {
Vector2D tgtPoint = tgtPoints;
double x = A * tgtPoint.getX() + B * tgtPoint.getY() + C;
value.setEntry(i, x);
// derivative with respect to x
jacobian.setEntry(i, 0, A);
// derivative with respect to y
jacobian.setEntry(i, 1, B);
// Constant
jacobian.setEntry(i, 1, 0.0);
}
return new Pair(value, jacobian);
}
};
/**
* @param refPoints reference points in the reference image
* @param tgtPoints corresponding target image positions
*/
TransformSolver(Vector2D[] refPoints, Vector2D[] tgtPoints, boolean fastCreate){
if (refPoints.length != tgtPoints.length)
throw new IllegalArgumentException("TransformSolver: input arrays have different lengths");
this.refPoints = refPoints;
this.tgtPoints = tgtPoints;
solveX();
solveY();
}
private void solveX(){
double[] refValues = new double[refPoints.length];
for (int i = 0; i < refPoints.length; i++){
refValues = refPoints.getX();
}
// least squares problem to solve
LeastSquaresProblem problem = new LeastSquaresBuilder().
start(new double[]{1.0, 0.0, 0.0}).
model(model).
target(refValues).
lazyEvaluation(false).
maxEvaluations(1000).
maxIterations(1000).
build();
LeastSquaresOptimizer.Optimum optimum = new LevenbergMarquardtOptimizer().optimize(problem);
System.out.println("A=" + optimum.getPoint().getEntry(0));
System.out.println("B=" + optimum.getPoint().getEntry(1));
System.out.println("C=" + optimum.getPoint().getEntry(2));
}
private void solveY(){
double[] refValues = new double[refPoints.length];
for (int i = 0; i < refPoints.length; i++){
refValues = refPoints.getY();
}
// least squares problem to solve
LeastSquaresProblem problem = new LeastSquaresBuilder().
start(new double[]{0.0, 1.0, 0.0}).
model(model).
target(refValues).
lazyEvaluation(false).
maxEvaluations(1000).
maxIterations(1000).
build();
LeastSquaresOptimizer.Optimum optimum = new LevenbergMarquardtOptimizer().optimize(problem);
System.out.println("D=" + optimum.getPoint().getEntry(0));
System.out.println("E=" + optimum.getPoint().getEntry(1));
System.out.println("F=" + optimum.getPoint().getEntry(2));
}
}
Подробнее здесь: https://stackoverflow.com/questions/787 ... -ax-by-c-y
Как использовать метод наименьших квадратов оптимизации Гиппарха для решения x' = Ax + By + C, y' = Dx + Ey + F (масштаб ⇐ JAVA
-
- Похожие темы
- Ответы
- Просмотры
- Последнее сообщение