73 const hdrl_imagelist * detlin)
75 const cpl_image * ima ;
76 const cpl_image * erra ;
77 const cpl_image * imb ;
78 const cpl_image * errb ;
79 const cpl_image * imc ;
80 const cpl_image * errc ;
82 const double * perra ;
84 const double * perrb ;
86 const double * perrc ;
91 double correction_factor;
95 if (!in || !detlin)
return -1 ;
110 if (!ima || !imb || !imc ) {
111 cpl_msg_error(cpl_func,
"Cannot access the detlin images") ;
114 pima = cpl_image_get_data_double_const(ima) ;
115 pimb = cpl_image_get_data_double_const(imb) ;
116 pimc = cpl_image_get_data_double_const(imc) ;
117 perra = cpl_image_get_data_double_const(erra);
118 perrb = cpl_image_get_data_double_const(errb);
119 perrc = cpl_image_get_data_double_const(errc);
123 nx = cpl_image_get_size_x(cur_ima) ;
124 ny = cpl_image_get_size_y(cur_ima) ;
125 if ((cpl_image_get_size_x(ima) != nx) ||
126 (cpl_image_get_size_x(imb) != nx) ||
127 (cpl_image_get_size_x(imc) != nx) ||
128 (cpl_image_get_size_y(ima) != ny) ||
129 (cpl_image_get_size_y(imb) != ny) ||
130 (cpl_image_get_size_y(imc) != ny)) {
131 cpl_msg_error(cpl_func,
"Incompatible sizes") ;
136 for (i=0 ; i<nx*ny ; i++) {
139 if (pdata[i] < CR2RES_DETLIN_THRESHOLD) continue ;
149 correction_factor = pima[i] + \
150 ((pimb[i] + pimc[i] * pdata[i]) * pdata[i]);
151 pdata[i] = pdata[i] * correction_factor;
177 const cpl_vector * dits,
178 const cpl_vector * adus,
180 cpl_polynomial ** fitted,
183 cpl_matrix * samppos ;
184 cpl_polynomial * fitted_local ;
185 cpl_vector * error_local ;
186 cpl_vector * adusPsec ;
187 cpl_vector * y_tofit, *tmp;
188 cpl_vector * adus_loc, *dits_loc;
190 cpl_size i=0, first_satur=-1 ;
194 if (fitted == NULL || dits == NULL || adus == NULL)
return -1 ;
195 if (cpl_vector_get_size(dits) != cpl_vector_get_size(adus))
199 if (cpl_vector_get_min(adus) > CR2RES_DETLIN_THRESHOLD)
return -1;
200 if (cpl_vector_get_max(adus) < CR2RES_DETLIN_THRESHOLD)
return -1;
201 for (i = 0; i < cpl_vector_get_size(adus); i++) {
202 if (cpl_vector_get(adus,i) < CR2RES_DETLIN_THRESHOLD ) count_linear++;
203 if (cpl_vector_get(adus,i)>CR2RES_DETLIN_MAXFIT && first_satur==-1)
208 if (first_satur==-1) first_satur= cpl_vector_get_size(dits);
210 if (count_linear > first_satur-1) count_linear = first_satur-1;
212 adus_loc = cpl_vector_extract(adus, 0, first_satur-1, 1);
213 dits_loc = cpl_vector_extract(dits, 0, first_satur-1, 1);
216 adusPsec = cpl_vector_duplicate(adus_loc);
217 cpl_vector_divide(adusPsec, dits_loc);
218 tmp = cpl_vector_extract(adusPsec,0,count_linear-1,1);
219 aduPsec = cpl_vector_get_median(tmp);
220 cpl_vector_delete(tmp);
222 samppos = cpl_matrix_wrap(1,
223 cpl_vector_get_size(adus_loc),
224 cpl_vector_get_data(adus_loc)) ;
226 y_tofit = cpl_vector_new(cpl_vector_get_size(dits_loc));
227 for(i = 0; i < cpl_vector_get_size(dits_loc); i++) {
230 y = aduPsec / cpl_vector_get(adusPsec,i);
231 cpl_vector_set(y_tofit, i, y);
233 cpl_vector_delete(adusPsec);
236 fitted_local = cpl_polynomial_new(1);
238 cpl_polynomial_fit(fitted_local, samppos, NULL, y_tofit, NULL,
239 CPL_FALSE, NULL, &max_degree) != CPL_ERROR_NONE) {
242 cpl_vector_delete(adus_loc);
243 cpl_vector_delete(dits_loc);
244 cpl_matrix_unwrap(samppos) ;
245 cpl_vector_delete(y_tofit);
246 cpl_polynomial_delete(fitted_local) ;
252 error_local = cpl_vector_new(max_degree+1) ;
253 cpl_size nc = max_degree + 1;
254 cpl_size ndata = cpl_vector_get_size(y_tofit);
257 for (i = 0; i < max_degree + 1; i++) {
258 cpl_vector_set(error_local, i, 0);
267 cpl_matrix * hankel = cpl_matrix_new(nc, nc);
268 cpl_matrix * mx = cpl_matrix_new(nc, 1);
272 cr2res_matrix_fill_normal_vandermonde(hankel, mx, adus_loc, CPL_FALSE,
274 cpl_matrix * inverse = cpl_matrix_invert_create(hankel);
275 cpl_vector * resids = cpl_vector_new(ndata);
277 cpl_vector_fill_polynomial_fit_residual(resids, y_tofit, NULL,
278 fitted_local, samppos, NULL);
279 for (i = 0; i < ndata; i++) {
280 cpl_vector_set(resids, i, fabs(cpl_vector_get(resids, i)));
283 cpl_matrix_multiply_scalar(inverse,
284 cpl_vector_get_sum(resids) / (
double)(ndata - nc));
286 for (i = 0; i < max_degree + 1; i++) {
287 cpl_vector_set(error_local, i, sqrt(cpl_matrix_get(inverse, i, i)));
289 cpl_matrix_delete(hankel);
290 cpl_matrix_delete(mx);
291 cpl_matrix_delete(inverse);
292 cpl_vector_delete(resids);
294 cpl_vector_delete(y_tofit);
295 cpl_matrix_unwrap(samppos) ;
296 cpl_vector_delete(dits_loc);
297 cpl_vector_delete(adus_loc);
300 for (i=0 ; i<=max_degree ; i++) {
302 cur_coeff = cpl_polynomial_get_coeff(fitted_local, &i) ;
303 if (isnan(cur_coeff)) {
304 cpl_polynomial_delete(fitted_local) ;
305 cpl_vector_delete(error_local) ;
313 if (cpl_error_get_code()) {
315 cpl_polynomial_delete(fitted_local) ;
316 cpl_vector_delete(error_local) ;
323 *fitted = fitted_local ;
324 if (error != NULL) *error = error_local ;
325 else cpl_vector_delete(error_local) ;