18 float sw, a1,
b1, a2, b2;
20 if (
fabs(wave - 555) > 2) {
21 if (
fabs(wave - 547) <= 2) {
27 }
else if (
fabs(wave - 550) <= 2) {
33 }
else if (
fabs(wave - 560) <= 2) {
39 }
else if (
fabs(wave - 565) <= 2) {
46 printf(
"-E- %s line %d: Unable to convert Rrs at %f to 555nm.\n", __FILE__, __LINE__, wave);
51 Rrs = pow(10.0, a1 * log10(
Rrs) -
b1);
85 void grabBricaud(
float wvl[],
int nwvl,
float* a_bricaud,
float* b_bricaud) {
87 float bricaud_L_A_B[][17] ={
88 {410, 412, 413, 440, 443, 488, 490, 510, 530, 531, 547, 550, 555, 560, 665, 667, 670},
89 {0.0313, 0.0323, 0.032775, 0.0403, 0.0394, 0.0279, 0.0274, 0.018, 0.0117, 0.0115, 0.00845,
90 0.008, 0.007, 0.0062, 0.0152, 0.01685, 0.0189},
91 {0.283, 0.286, 0.28775, 0.332, 0.3435, 0.369, 0.361, 0.260, 0.139, 0.134, 0.0625,
92 0.052, 0.0315, 0.016, 0.134, 0.140, 0.149}
104 while (ko < nwvl && srchCounter < wvlToSrch) {
106 if (wvl[ko] == bricaud_L_A_B[0][kb]) {
107 a_bricaud[ko] = bricaud_L_A_B[1][kb];
108 b_bricaud[ko] = bricaud_L_A_B[2][kb];
111 }
else if (wvl[ko] < bricaud_L_A_B[0][kb]) {
121 void grabAwBw(
float wvl[],
int nwvl,
float aw[],
float bw[]) {
123 for (
i = 0;
i < nwvl;
i++) {
165 void calcQAA443(
float ab_surf_rrs[],
float wvl[],
int nwvl, ccstr *ctxt) {
167 float *blw_surf_rrs, *u_ptr;
168 float c1 = 0.52, c2 = 1.7;
169 float g0 = 0.089, g1 = 0.125;
170 float a0, bbp0, bbp0_exp, a0_exp;
171 float ratio_aph, slope_adg, ratio_adg;
172 static int firstCall = 1;
173 static int rIdx = -1, gIdx = -1, bgIdx = -1, refIdx = -1, purIdx = -1;
175 blw_surf_rrs = (
float*) malloc(nwvl *
sizeof (
float));
176 u_ptr = (
float*) malloc(nwvl *
sizeof (
float));
180 rIdx =
windex(670, wvl, nwvl);
181 gIdx =
windex(550, wvl, nwvl);
182 bgIdx =
windex(490, wvl, nwvl);
184 purIdx =
windex(412, wvl, nwvl);
187 float bbp[refIdx + 1],
a[refIdx + 1];
189 float up_667 = 20 * pow(ab_surf_rrs[gIdx], 1.5);
190 float lw_667 = 0.9 * pow(ab_surf_rrs[gIdx], 1.7);
191 if (ab_surf_rrs[rIdx] > up_667 || ab_surf_rrs[rIdx] < lw_667) {
192 ab_surf_rrs[rIdx] = 1.27 * pow(ab_surf_rrs[gIdx], 1.47) +
193 0.00018 * pow(ab_surf_rrs[gIdx] / (ab_surf_rrs[bgIdx]), -3.19);
198 for (ib = 0; ib < nwvl; ib++) {
200 *(blw_surf_rrs + ib) = ab_surf_rrs[ib] / (c1 + c2 * ab_surf_rrs[ib]);
201 *(u_ptr + ib) = (-g0 + pow(pow(g0, 2) + 4 * g1 *
202 *(blw_surf_rrs + ib), 0.5)) / (2 * g1);
205 (*(blw_surf_rrs + refIdx) + *(blw_surf_rrs + bgIdx)) /
206 (*(blw_surf_rrs + gIdx) + 5 * (*(blw_surf_rrs + rIdx) /
207 *(blw_surf_rrs + bgIdx)) *
208 *(blw_surf_rrs + rIdx))
210 a0 = *(ctxt->aw_i + gIdx) + pow(10.0, (-1.146 - (1.366 * a0_exp) -(0.469 * pow(a0_exp, 2))));
211 bbp0 = *(u_ptr + gIdx) * a0 / (1 - *(u_ptr + gIdx)) - *(ctxt->bbw_i + gIdx);
212 bbp0_exp = 2 * (1 - 1.2 * exp(-0.9 * *(blw_surf_rrs + refIdx) / *(blw_surf_rrs + gIdx)));
213 ratio_aph = 0.74 + (0.2 / (0.8 + *(blw_surf_rrs + refIdx) / *(blw_surf_rrs + gIdx)));
214 slope_adg = 0.015 + 0.002 / (0.6 + *(blw_surf_rrs + refIdx) / *(blw_surf_rrs + gIdx));
215 ratio_adg = exp(slope_adg * (wvl[refIdx] - wvl[purIdx]));
216 for (ib = 0; ib <= refIdx; ib++) {
218 bbp[ib] = bbp0 * pow((wvl[gIdx] / wvl[ib]), bbp0_exp);
219 a[ib] = (1 - *(u_ptr + ib)) * (bbp[ib] + *(ctxt->bbw_i + ib)) / *(u_ptr + ib);
221 *(ctxt->adgRef) = ((
a[purIdx] - ratio_aph *
a[refIdx]) - (*(ctxt->aw_i + purIdx) - ratio_aph * *(ctxt->aw_i + refIdx))) /
222 (ratio_adg - ratio_aph);
223 *(ctxt->aphRef) =
a[refIdx] - *(ctxt->aw_i + refIdx) - *(ctxt->adgRef);
224 *(ctxt->bbpRef) = bbp[refIdx];
238 for (in = 0; in<*ctxt->num_wvl_i; in++) {
239 wt = 1.0 /
fabs(ctxt->wvl_i[in] - xout);
240 prodSum += wt * ctxt->tar_rrs[in];
244 interpOut = prodSum / wtSum;
252 void idInputBand(
float inputWvl[],
float targetWvl, ccstr *ctxt,
int nin) {
262 closeIdx =
windex(targetWvl, inputWvl, nin);
263 if (((inputWvl[closeIdx] - targetWvl) >
MINWVDIFF) && (closeIdx > 0)) {
264 idx[0] = closeIdx - 1;
266 }
else if (((inputWvl[closeIdx] - targetWvl) < -
MINWVDIFF) && (closeIdx < (nin - 1))) {
268 idx[1] = closeIdx + 1;
273 ctxt->sh_strt_idx = (
int*) malloc(nout *
sizeof (
int));
274 ctxt->wvl_i = (
float*) malloc(nout *
sizeof (
float));
275 ctxt->num_wvl_i = (
int*) malloc(
sizeof (
int));
276 *(ctxt->num_wvl_i) = nout;
278 for (kb = 0; kb < nout; kb++) {
279 *(ctxt->sh_strt_idx + kb) = idx[kb];
280 *(ctxt->wvl_i + kb) = inputWvl[idx[kb]];
290 void shiftBand(
float inputWvl[],
float inputRrs[],
float chla,
int numBands,
float tarWvl, ccstr* ctxt)
293 float wvlIn, rrsIn, refwvl;
294 float s = 0.015, g0 = 0.089, g1 = 0.125, c1 = -0.52, c2 = 1.7;
295 static int gIdx = -1, refIdx = -1;
297 float ll_i, aph_i, adg_i, bbp_i;
298 float a_tot_i, bb_tot_i, qaa_fwd_i, qaa_rrs_bbw_i, qaa_rrs_aw_i;
299 float ll_o, aph_o, adg_o, bbp_o;
300 float a_tot_o, bb_tot_o, qaa_fwd_o, qaa_rrs_bbw_o, qaa_rrs_aw_o, correc_factor;
305 gIdx =
windex(550, inputWvl, numBands);
308 refwvl = inputWvl[refIdx];
310 nin = *(ctxt->num_wvl_i);
312 b2g = inputRrs[refIdx] / inputRrs[gIdx];
313 sdg =
s + 0.002 / (0.6 + b2g);
314 yy = 2 * (1 - 1.2 * exp(-0.9 * b2g));
317 for (kb = 0; kb < nin; kb++) {
318 idx = *(ctxt->sh_strt_idx + kb);
319 wvlIn = inputWvl[idx];
320 rrsIn = inputRrs[idx];
322 ll_i = wvlIn - refwvl;
324 adg_i = *(ctxt->adgRef) * exp(-sdg * ll_i);
325 bbp_i = *(ctxt->bbpRef) * pow((443 / wvlIn), yy);
326 a_tot_i = aph_i + adg_i + *(ctxt->aw_i + idx);
327 bb_tot_i = bbp_i + *(ctxt->bbw_i + idx);
328 qaa_fwd_i = bb_tot_i / (a_tot_i + bb_tot_i);
329 qaa_rrs_bbw_i = (g0 + g1 * qaa_fwd_i) * qaa_fwd_i;
330 qaa_rrs_aw_i = (c1 * qaa_rrs_bbw_i) / ((c2 * qaa_rrs_bbw_i) - 1);
334 adg_o = *(ctxt->adgRef) * exp(-sdg * ll_o);
335 bbp_o = *(ctxt->bbpRef) * pow((443 / tarWvl), yy);
336 a_tot_o = aph_o + adg_o + *(ctxt->aw_o);
337 bb_tot_o = bbp_o + *(ctxt->bbw_o);
338 qaa_fwd_o = bb_tot_o / (a_tot_o + bb_tot_o);
339 qaa_rrs_bbw_o = (g0 + g1 * qaa_fwd_o) * qaa_fwd_o;
340 qaa_rrs_aw_o = (c1 * qaa_rrs_bbw_o) / ((c2 * qaa_rrs_bbw_o) - 1);
341 correc_factor = qaa_rrs_aw_o / qaa_rrs_aw_i;
342 *(ctxt->tar_rrs + kb) = rrsIn * correc_factor;
360 free(ctxt->num_wvl_i);
362 free(ctxt->sh_strt_idx);
366 float bioBandShift(
float wvl[],
float rrs[],
float chla,
int nw,
float tarWvl) {
370 sh_ctxt.aw_i = (
float*) malloc(nw *
sizeof (
float));
371 sh_ctxt.bbw_i = (
float*) malloc(nw *
sizeof (
float));
372 sh_ctxt.aBric_i = (
float*) malloc(nw *
sizeof (
float));
373 sh_ctxt.bBric_i = (
float*) malloc(nw *
sizeof (
float));
374 sh_ctxt.aw_o = (
float*) malloc(
sizeof (
float));
375 sh_ctxt.bbw_o = (
float*) malloc(
sizeof (
float));
376 sh_ctxt.aBric_o = (
float*) malloc(
sizeof (
float));
377 sh_ctxt.bBric_o = (
float*) malloc(
sizeof (
float));
378 sh_ctxt.aphRef = (
float*) malloc(
sizeof (
float));
379 sh_ctxt.adgRef = (
float*) malloc(
sizeof (
float));
380 sh_ctxt.bbpRef = (
float*) malloc(
sizeof (
float));
381 sh_ctxt.tar_rrs = (
float*) malloc(
sizeof (
float));
383 grabAwBw(wvl, nw, sh_ctxt.aw_i, sh_ctxt.bbw_i);
384 grabAwBw(&tarWvl, 1, sh_ctxt.aw_o, sh_ctxt.bbw_o);
387 shiftBand(wvl, rrs, chla, nw, tarWvl, &sh_ctxt);
388 if (*sh_ctxt.num_wvl_i > 1)
392 result = *(sh_ctxt.tar_rrs);