I am using opencv to do Exposure Compensate with GainCompensator method.
error equation:
above equation's derivative:
Set to 0:
I replace OpenCV code (line 127~141) with ceres-solver, like below:
---------------
struct F {
F(int Nij, double Iij, double Iji, double alpha, double beta) :Nij_(Nij), Iij_(Iij), Iji_(Iji), alpha_(alpha), beta_(beta) {}
template <typename T> bool operator()(const T* const gi, const T* const gj, T* residual) const {
residual[0] = T(Nij_) * ( alpha_ * alpha_ * (gi[0] * Iij_ - gj[0] * Iji_) * (gi[0] * Iij_ - gj[0] * Iji_) + beta_ * beta_ * (T(1) - gi[0]) * (T(1) - gi[0]) );
return true;
}
private:
const int Nij_;
const double Iij_, Iji_, alpha_, beta_;
};
struct E {
E(int Nij, double beta) :Nij_(Nij), beta_(beta) {}
template <typename T> bool operator()(const T* const gi, T* residual) const {
residual[0] = T(Nij_) * (beta_ * beta_ * (T(1) - gi[0]) * (T(1) - gi[0]));
return true;
}
private:
const int Nij_;
const double beta_;
};
---------------
//google::InitGoogleLogging("");
gains_ = Mat_<double>::zeros(num_images, 1);
for (int i = 0; i < num_images; ++i) {
gains_(i, 0) = 0; // if I set to all 1, then it will output all 1.
}
ceres::Problem problem;
for (int i = 0; i < num_images; ++i)
{
for (int j = 0; j < num_images; ++j)
{
if (i != j)
problem.AddResidualBlock(new AutoDiffCostFunction<F, 1, 1, 1>(new F(N(i, j), I(i, j), I(j, i), alpha, beta)), NULL, &gains_(i, 0), &gains_(j, 0));
else
problem.AddResidualBlock(new AutoDiffCostFunction<E, 1, 1>(new E(N(i, j), beta)), NULL, &gains_(i, 0));
}
}
ceres::Solver::Options options;
//options.max_num_iterations = 25;
options.linear_solver_type = ceres::DENSE_QR;
options.num_linear_solver_threads = 4;
options.function_tolerance = 0.1;
options.minimizer_progress_to_stdout = true;
ceres::Solver::Summary summary;
ceres::Solve(options, &problem, &summary);
//std::cout << summary.BriefReport() << "\n";
----------------
I use seven images to test exposure compensate, ceres-solver quick a little, but the answer is not what I want.
I think this is because ceres-solver is getting a local solution, how can I get the same answer the same with Opencv, because ceres-solver is very easy to use.
Does anyone know more about math with this problem, thank you very much!