Changeset 27531 for trunk/psModules/src/objects/models/pmModel_QGAUSS.c
- Timestamp:
- Mar 30, 2010, 1:29:50 PM (16 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/psModules/src/objects/models/pmModel_QGAUSS.c
r26916 r27531 39 39 # define PM_MODEL_SET_LIMITS pmModelSetLimits_QGAUSS 40 40 41 # define ALPHA 2.250 42 # define ALPHA_M 1.250 43 41 44 // the model is a function of the pixel coordinate (pixcoord[0,1] = x,y) 42 45 // 0.5 PIX: the parameters are defined in terms of pixel coords, so the incoming pixcoords … … 44 47 45 48 // Lax parameter limits 46 static float paramsMinLax[] = { -1.0e3, 1.0e-2, -100, -100, 0.5, 0.5, -1.0, 0.1};49 static float paramsMinLax[] = { -1.0e3, 1.0e-2, -100, -100, 0.5, 0.5, -1.0, -1.0 }; 47 50 static float paramsMaxLax[] = { 1.0e5, 1.0e8, 1.0e4, 1.0e4, 100, 100, 1.0, 20.0 }; 48 51 49 52 // Moderate parameter limits 50 static float *paramsMinModerate = paramsMinLax; 51 static float *paramsMaxModerate = paramsMaxLax; 53 // Tolerate a small divot (k < 0) 54 static float paramsMinModerate[] = { -1.0e3, 1.0e-2, -100, -100, 0.5, 0.5, -1.0, -0.05 }; 55 static float paramsMaxModerate[] = { 1.0e5, 1.0e8, 1.0e4, 1.0e4, 100, 100, 1.0, 20.0 }; 52 56 53 57 // Strict parameter limits 54 static float *paramsMinStrict = paramsMinLax; 55 static float *paramsMaxStrict = paramsMaxLax; 58 // k = PAR_7 < 0 is very undesirable (big divot in the middle) 59 static float paramsMinStrict[] = { -1.0e3, 1.0e-2, -100, -100, 0.5, 0.5, -1.0, 0.0 }; 60 static float paramsMaxStrict[] = { 1.0e5, 1.0e8, 1.0e4, 1.0e4, 100, 100, 1.0, 20.0 }; 56 61 57 62 // Parameter limits to use 58 63 static float *paramsMinUse = paramsMinLax; 59 64 static float *paramsMaxUse = paramsMaxLax; 60 static float betaUse[] = { 1000, 3e6, 5, 5, 1.0, 1.0, 0.5 };65 static float betaUse[] = { 1000, 3e6, 5, 5, 1.0, 1.0, 0.5, 2.0 }; 61 66 62 67 static bool limitsApply = true; // Apply limits? … … 81 86 assert (z >= 0); 82 87 83 psF32 zp = pow(z, 1.25);88 psF32 zp = pow(z,ALPHA_M); 84 89 psF32 r = 1.0 / (1 + PAR[PM_PAR_7]*z + z*zp); 85 90 … … 92 97 // note difference from a pure gaussian: q = params->data.F32[PM_PAR_I0]*r 93 98 psF32 t = r1*r; 94 psF32 q = t*(PAR[PM_PAR_7] + 2.25*zp);99 psF32 q = t*(PAR[PM_PAR_7] + ALPHA*zp); 95 100 96 101 dPAR[PM_PAR_SKY] = +1.0; … … 246 251 float f1, f2; 247 252 for (z = DZ; z < 50; z += DZ) { 248 f1 = 1.0 / (1 + PAR[PM_PAR_7]*z + pow(z, 2.25));253 f1 = 1.0 / (1 + PAR[PM_PAR_7]*z + pow(z, ALPHA)); 249 254 z += DZ; 250 f2 = 1.0 / (1 + PAR[PM_PAR_7]*z + pow(z, 2.25));255 f2 = 1.0 / (1 + PAR[PM_PAR_7]*z + pow(z, ALPHA)); 251 256 norm += f0 + 4*f1 + f2; 252 257 f0 = f2; … … 263 268 psF64 PM_MODEL_RADIUS (const psVector *params, psF64 flux) 264 269 { 265 psF64 z , f;270 psF64 z; 266 271 int Nstep = 0; 267 272 psEllipseShape shape; … … 269 274 psF32 *PAR = params->data.F32; 270 275 271 if (flux <= 0) 272 return (1.0); 273 if (PAR[PM_PAR_I0] <= 0) 274 return (1.0); 275 if (flux >= PAR[PM_PAR_I0]) 276 return (1.0); 276 if (flux <= 0) return 1.0; 277 if (PAR[PM_PAR_I0] <= 0) return 1.0; 278 if (flux >= PAR[PM_PAR_I0]) return 1.0; 279 if (PAR[PM_PAR_7] == 0.0) return powf(PAR[PM_PAR_I0] / flux - 1.0, 1.0 / ALPHA); 277 280 278 281 shape.sx = PAR[PM_PAR_SXX] / M_SQRT2; … … 290 293 291 294 // choose a z value guaranteed to be beyond our limit 292 float z0 = pow((1.0 / limit), (1.0 / 2.25)); 293 psAssert (isfinite(z0), "fix this code: z0 should not be nan for %f", PAR[PM_PAR_7]); 294 float z1 = (1.0 / limit) / PAR[PM_PAR_7]; 295 float z0 = 0.0; 296 float z1 = pow((1.0 / limit), (1.0 / ALPHA)); 295 297 psAssert (isfinite(z1), "fix this code: z1 should not be nan for %f", PAR[PM_PAR_7]); 296 z1 = PS_MAX (z0, z1); 297 z0 = 0.0; 298 299 // perform a type of bisection to find the value 300 float f0 = 1.0 / (1 + PAR[PM_PAR_7]*z0 + pow(z0, 2.25)); 301 float f1 = 1.0 / (1 + PAR[PM_PAR_7]*z1 + pow(z1, 2.25)); 302 while ((Nstep < 10) && (fabs(z1 - z0) > 0.5)) { 303 z = 0.5*(z0 + z1); 304 f = 1.0 / (1 + PAR[PM_PAR_7]*z + pow(z, 2.25)); 305 if (f > limit) { 306 z0 = z; 307 f0 = f; 308 } else { 309 z1 = z; 310 f1 = f; 311 } 312 Nstep ++; 298 if (PAR[PM_PAR_7] < 0.0) z1 *= 2.0; 299 300 // starting guess: 301 z = 0.5*(z0 + z1); 302 float dz = 1.0; 303 304 // use Newton-Raphson to minimize f(z) - limit = 0 305 for (int i = 0; (i < 10) && (fabs(dz) > 0.0001); i++) { 306 float q = (1.0 + PAR[PM_PAR_7]*z + pow(z, ALPHA)); 307 float dqdz = (PAR[PM_PAR_7] + ALPHA*pow(z, ALPHA - 1.0)); 308 309 float f = 1.0 / q; 310 float dfdz = -dqdz * f / q; 311 312 dz = (f - limit) / dfdz; 313 314 // fprintf (stderr, "%f %f %f : %f %f\n", f, z, dz, dfdz, q); 315 z -= dz; 313 316 } 314 317 psF64 radius = sigma * sqrt (2.0 * z); … … 475 478 # undef PM_MODEL_FIT_STATUS 476 479 # undef PM_MODEL_SET_LIMITS 480 # undef ALPHA 481 # undef ALPHA_M
Note:
See TracChangeset
for help on using the changeset viewer.
