106 template<
typename Target>
120 this->compute_derivatives(
target);
129 for (
size_t j = 0;
j <
na;
j++)
136 for (
size_t i = 0;
i <
na;
i++)
142#ifdef GEMMI_DEBUG_LEVMAR
143 fprintf(
stderr,
" #%d WSSR=%.8g %+g%% (%+.4g%%) lambda=%g\n",
165 this->compute_derivatives(
target);
179 template<
typename Target>
184#ifdef GEMMI_DEBUG_LEVMAR
188 std::fill(
beta.begin(),
beta.end(), 0.0);
192 std::vector<double>
dy_da;
193 size_t n =
target.points.size();
196 std::vector<double>
yy(
tsize, 0.);
200 for (
size_t i = 0;
i !=
tsize; ++
i) {
204 for (
int j = 0;
j !=
na; ++
j) {
207 for (
int k =
j;
k != -1; --
k)
216 for (
int j = 1; j < na; j++)
217 for (
int k = 0; k < j; k++)
221#ifdef GEMMI_DEBUG_LEVMAR
222 template<
typename Target>
223 void check_derivatives(Target& target) {
224 assert(!
beta.empty());
226 std::vector<double> yy(target.points.size(), 0.);
227 std::vector<double> dy_da(target.points.size() *
beta.size());
228 target.compute_values_and_derivatives(0, target.points.size(), yy, dy_da);
229 std::vector<double> yy2 = target.compute_values();
230 assert(yy.size() == yy2.size());
231 for (
size_t i = 0; i != yy.size(); ++i) {
232 double m = std::max(std::fabs(yy[i]), std::fabs(yy2[i]));
233 if (m > 1e-5 && std::fabs(yy[i] - yy2[i]) > 1e-6 * m)
234 fprintf(stderr,
"!! value %zu: %g != %g\n", i, yy[i], yy2[i]);
236 const double numerical_h = 1e-3;
237 const double small_number = 1e-6;
238 std::vector<double> aa = target.get_parameters();
239 assert(aa.size() ==
beta.size());
240 for (
size_t k = 0; k < aa.size(); k++) {
241 double acopy = aa[k];
242 double h = std::max(std::fabs(acopy), small_number) * numerical_h;
244 target.set_parameters(aa);
245 std::vector<double> y_left = target.compute_values();
247 target.set_parameters(aa);
248 std::vector<double> y_right = target.compute_values();
250 for (
size_t i = 0; i != target.points.size(); ++i) {
251 double symbolic = dy_da[i * aa.size() + k];
252 double numeric = (y_right[i] - y_left[i]) / (2 * h);
253 double m = std::max(std::fabs(symbolic), std::fabs(numeric));
254 if (m > 1e-3 && std::fabs(symbolic - numeric) > 0.02 * m)
255 fprintf(stderr,
"!! dy[%zu]/da[%zu]: %g != %g\n", i, k, symbolic, numeric);
260 target.set_parameters(aa);
264 template<
typename Po
int>
265 double compute_wssr(
const std::vector<double>& yy,
const std::vector<Point>& data) {
267 long double wssr = 0;
268 for (
int j = 0; j < (int)yy.size(); j++) {
269 double dy = data[j].get_weight() * (data[j].get_y() - yy[j]);
273 return (
double) wssr;