00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119 #include <stdio.h>
00120 #include <lal/LALInspiralBank.h>
00121 #include <lal/AVFactories.h>
00122 #include <lal/SeqFactories.h>
00123 #include <lal/LALStdio.h>
00124 #include <lal/FindRoot.h>
00125
00126
00127
00128
00129
00130 void
00131 LALPopulateNarrowEdge(LALStatus *status,
00132 InspiralMomentsEtc *moments,
00133 InspiralCell **cell,
00134 INT4 headId,
00135 InspiralTemplate *paramsIn,
00136 HexaGridParam *gridParam,
00137 CellEvolution *cellEvolution,
00138 CellList **cellList,
00139 INT4 flag
00140 );
00141
00142
00143 NRCSID(LALINSPIRALHYBRIDHEXAGONALBANKC, "$Id: LALInspiralHybridHexagonalBank.c,v 1.7 2007/06/08 14:41:42 bema Exp $");
00144
00145
00146 void
00147 LALInspiralCreatePNCoarseBankHybridHexa(
00148 LALStatus *status,
00149 InspiralTemplateList **list,
00150 INT4 *nlist,
00151 InspiralCoarseBankIn coarseIn
00152 )
00153 {
00154 INT4 i;
00155 INT4 firstId = 0;
00156 REAL4 A0, A3;
00157 REAL4 piFl;
00158 InspiralBankParams bankPars;
00159 InspiralTemplate *tempPars;
00160 InspiralMomentsEtc moments;
00161 InspiralCell *cells;
00162 HexaGridParam gridParam;
00163 CellEvolution cellEvolution;
00164 CellList *cellList = NULL;
00165
00166 INITSTATUS( status, "LALInspiralHybridHexagonalBank",
00167 LALINSPIRALHYBRIDHEXAGONALBANKC );
00168 ATTATCHSTATUSPTR( status );
00169
00170 ASSERT( coarseIn.mMin > 0., status,
00171 LALINSPIRALBANKH_ESIZE, LALINSPIRALBANKH_MSGESIZE );
00172 ASSERT( coarseIn.mMax > 0., status,
00173 LALINSPIRALBANKH_ESIZE, LALINSPIRALBANKH_MSGESIZE );
00174 ASSERT( coarseIn.MMax >= 2.*coarseIn.mMin, status,
00175 LALINSPIRALBANKH_ESIZE, LALINSPIRALBANKH_MSGESIZE );
00176
00177
00178
00179 if ( !(tempPars = (InspiralTemplate *)
00180 LALCalloc( 1, sizeof(InspiralTemplate))))
00181 {
00182 LALFree(tempPars);
00183 LALFree(cells);
00184 ABORT( status, LALINSPIRALBANKH_EMEM, LALINSPIRALBANKH_MSGEMEM );
00185 }
00186
00187
00188 LALInspiralSetParams( status->statusPtr, tempPars, coarseIn );
00189 CHECKSTATUSPTR( status );
00190
00191
00192
00193 LALInspiralSetSearchLimits( status->statusPtr, &bankPars, coarseIn );
00194 CHECKSTATUSPTR( status );
00195
00196 tempPars->totalMass = coarseIn.MMax;
00197 tempPars->eta = 0.25;
00198 tempPars->ieta = 1.L;
00199 tempPars->fLower = coarseIn.fLower;
00200 tempPars->massChoice = m1Andm2;
00201 tempPars->mass1 = coarseIn.mMin;
00202 tempPars->mass2 = coarseIn.mMax;
00203
00204 LALInspiralParameterCalc( status->statusPtr, tempPars );
00205 CHECKSTATUSPTR( status );
00206
00207
00208
00209 LALGetInspiralMoments(
00210 status->statusPtr,
00211 &moments,
00212 &coarseIn.shf,
00213 tempPars );
00214 CHECKSTATUSPTR( status );
00215
00216
00217 cells = (InspiralCell*)
00218 LALCalloc(1, sizeof(InspiralCell) );
00219
00220
00221 gridParam.mm = coarseIn.mmCoarse;
00222 gridParam.x0Min = bankPars.x0Min;
00223 gridParam.x0Max = bankPars.x0Max;
00224 gridParam.x1Min = bankPars.x1Min;
00225 gridParam.x1Max = bankPars.x1Max;
00226 gridParam.mMin = coarseIn.mMin;
00227 gridParam.mMax = coarseIn.mMax;
00228 gridParam.MMin = coarseIn.MMin;
00229 gridParam.MMax = coarseIn.MMax;
00230 gridParam.etaMin = coarseIn.etamin;
00231 gridParam.space = coarseIn.space;
00232 gridParam.massRange = coarseIn.massRange;
00233 gridParam.gridSpacing = coarseIn.gridSpacing;
00234 gridParam.fLower = coarseIn.fLower;
00235
00236
00237 cellEvolution.nTemplate = 1;
00238 cellEvolution.nTemplateMax = 1;
00239 cellEvolution.fertile = 0;
00240
00241
00242 tempPars->massChoice = t03;
00243 cells[0].t0 = tempPars->t0;
00244 cells[0].t3 = tempPars->t3;
00245
00246
00247 piFl = LAL_PI * tempPars->fLower;
00248 A0 = 5. / pow(piFl, 8./3.) / 256.;
00249 A3 = LAL_PI / pow(piFl, 5./3.)/8.;
00250
00251
00252
00253 LALInitHexagonalBank(
00254 status->statusPtr,
00255 &cells, firstId,
00256 &moments, tempPars,
00257 &gridParam, &cellEvolution,
00258 &cellList);
00259 CHECKSTATUSPTR( status );
00260
00261
00262 {
00263 INT4 k, kk;
00264 INT4 *list = NULL;
00265 CellList *ptr = NULL;
00266 INT4 length = 1;
00267
00268
00269
00270
00271 if (! (list = LALMalloc(length*sizeof(INT4))))
00272 {
00273 ABORT( status, LALINSPIRALBANKH_EMEM, LALINSPIRALBANKH_MSGEMEM );
00274 }
00275
00276
00277 while (cellEvolution.fertile)
00278 {
00279 length = LALListLength(cellList);
00280
00281 if (! (list = LALRealloc(list, length*sizeof(INT4))))
00282 {
00283 ABORT( status, LALINSPIRALBANKH_EMEM, LALINSPIRALBANKH_MSGEMEM );
00284
00285 }
00286 ptr = cellList;
00287
00288
00289
00290 for ( k = 0; k < length; k++)
00291 {
00292 list[k] = ptr->id;
00293 ptr = ptr->next;
00294 }
00295
00296 for (kk = 0; kk < length; kk++)
00297 {
00298 k = list[kk];
00299 if ( cells[k].status == Fertile)
00300 {
00301 LALPopulateCell(status->statusPtr, &moments, &cells,
00302 k, tempPars, &gridParam, &cellEvolution, &cellList);
00303 CHECKSTATUSPTR( status );
00304
00305
00306
00307
00308 }
00309 }
00310 }
00311 LALFree(list);
00312 }
00313
00314 #if 1
00315 {
00316
00317
00318
00319 INT4 edge1=0, edge2=0;
00320
00321 gridParam.gridSpacing = Hexagonal;
00322
00323 i=0;
00324 while (i<cellEvolution.nTemplate){
00325 if (cells[i].status == Edge){
00326 edge1 = i;
00327 cells[i].status = In;
00328 i=cellEvolution.nTemplate;
00329 }
00330 i++;
00331 }
00332 i=0;
00333 while (i<cellEvolution.nTemplate){
00334 if (cells[i].status == Edge){
00335 edge2=i;
00336 cells[i].status = In;
00337 i=cellEvolution.nTemplate;
00338 }
00339 i++;
00340 }
00341
00342
00343
00344 if (cells[edge1].t0 > cells[edge2].t0){
00345 LALPopulateNarrowEdge(status->statusPtr, &moments, &cells,
00346 edge1, tempPars, &gridParam, &cellEvolution, &cellList, 0);
00347 CHECKSTATUSPTR( status );
00348 LALPopulateNarrowEdge(status->statusPtr, &moments, &cells,
00349 edge2, tempPars, &gridParam, &cellEvolution, &cellList, 1);
00350 CHECKSTATUSPTR( status );
00351 }
00352 else
00353 {
00354 LALPopulateNarrowEdge(status->statusPtr, &moments, &cells,
00355 edge1, tempPars, &gridParam, &cellEvolution, &cellList, 1);
00356 CHECKSTATUSPTR( status );
00357 LALPopulateNarrowEdge(status->statusPtr, &moments, &cells,
00358 edge2, tempPars, &gridParam, &cellEvolution, &cellList, 0);
00359 CHECKSTATUSPTR( status );
00360 }
00361 }
00362
00363
00364 #endif
00365
00366
00367
00368 if (cellList != NULL)
00369 ABORT(status, LALINSPIRALBANKH_EHEXAINIT,LALINSPIRALBANKH_MSGEHEXAINIT);
00370
00371
00372
00373 *nlist = cellEvolution.nTemplate;
00374
00375 {
00376 INT4 k ;
00377 INT4 length;
00378 length = cellEvolution.nTemplate;
00379
00380 for ( k = 0; k < length; k++)
00381 {
00382 REAL4 a;
00383 REAL4 b;
00384 REAL4 x0;
00385 REAL4 tempA3;
00386 SFindRootIn input;
00387 INT4 valid;
00388
00389 PRIN prin;
00390
00391 tempA3 = pow(A3, -5./2.)/pow(0.25,-1.5);
00392 tempPars->t0 = cells[k].t0;
00393 tempPars->t3 = cells[k].t3;
00394
00395 if(cells[k].RectPosition[0] == Below )
00396 {
00397 INT4 above=0, below=0, in=0, out=0;
00398
00399
00400
00401
00402
00403 a = tan(cells[k].metric.theta);
00404 b = cells[k].t3 - a * cells[k].t0;
00405
00406 input.function = LALSPAF;
00407 input.xmin = cells[k].t3-1e-3;
00408 input.xmax = 1000;
00409 input.xacc = 1e-6;
00410
00411 prin.ct = a * A0 * tempA3;
00412 prin.b = b;
00413
00414 LALSBisectionFindRoot(status->statusPtr,
00415 &x0, &input, (void *)&prin);
00416 CHECKSTATUSPTR( status );
00417
00418 tempPars->t3 = x0 + 1e-3;
00419 tempPars->t0 = (tempPars->t3 - b)/a;
00420 if (tempPars->t0 > 0)
00421 {
00422 LALInspiralParameterCalc(status->statusPtr, tempPars);
00423 CHECKSTATUSPTR( status );
00424 }
00425 else
00426 {
00427 LALWarning(status,"HybridHexagonal placement: nothing to be done since t0<=0\n");
00428 }
00429
00430 cells[k].t0 = tempPars->t0;
00431 cells[k].t3 = tempPars->t3;
00432
00433
00434 valid = 1;
00435 GetPositionRectangle(status->statusPtr, &cells, k, tempPars ,
00436 &gridParam,
00437 &cellEvolution,
00438 &cellList,
00439 &valid);
00440 {
00441
00442 switch (cells[k].RectPosition[1]){
00443 case In: in +=1; break;
00444 case Below: below +=1; break;
00445 case Above: above +=1; break;
00446 case Out: out +=1; break;
00447 }
00448 switch (cells[k].RectPosition[2]){
00449 case In: in +=1; break;
00450 case Below: below +=1; break;
00451 case Above: above +=1; break;
00452 case Out: out +=1; break;
00453 }
00454 switch (cells[k].RectPosition[3]){
00455 case In: in +=1; break;
00456 case Below: below +=1; break;
00457 case Above: above +=1; break;
00458 case Out: out +=1; break;
00459 }
00460 switch (cells[k].RectPosition[4]){
00461 case In: in +=1; break;
00462 case Below: below +=1; break;
00463 case Above: above +=1; break;
00464 case Out: out +=1; break;
00465 }
00466 }
00467
00468
00469 if (above == 2 && cells[k].position == In)
00470 {
00471 if (cells[k].child[0] >=0 )
00472 {
00473 cells[cells[k].child[0]].position = Out;
00474 }
00475 else
00476 {
00477
00478 }
00479
00480 }
00481 else
00482 {
00483
00484 }
00485 }
00486 else
00487 {
00488
00489 }
00490 }
00491 }
00492
00493 for (i=0; i<cellEvolution.nTemplate; i++) {
00494 if (cells[i].position == In ) {
00495 *nlist = *nlist +1;
00496 }
00497 }
00498
00499
00500
00501
00502 *list = (InspiralTemplateList*)
00503 LALRealloc( *list, sizeof(InspiralTemplateList) * (*nlist+1) );
00504 if ( ! *list )
00505 {
00506 LALFree( tempPars );
00507 ABORT( status, LALINSPIRALBANKH_EMEM, LALINSPIRALBANKH_MSGEMEM );
00508 }
00509 memset( *list + *nlist, 0, sizeof(InspiralTemplateList) );
00510 {
00511 *nlist = 0 ;
00512 for (i=0; i<cellEvolution.nTemplate; i++)
00513 {
00514 if (cells[i].position == In & cells[i].t0>0)
00515 {
00516 tempPars->t0 = cells[i].t0;
00517 tempPars->t3 = cells[i].t3;
00518 tempPars->massChoice = t03;
00519 tempPars->fLower = coarseIn.fLower;
00520 LALInspiralParameterCalc( status->statusPtr, tempPars );
00521 CHECKSTATUSPTR( status );
00522
00523 (*list)[*nlist].ID = *nlist;
00524 (*list)[*nlist].params = *tempPars;
00525 (*list)[*nlist].metric = cells[i].metric;
00526 ++(*nlist);
00527 }
00528 }
00529 }
00530
00531
00532 LALFree( cells );
00533 LALFree( tempPars );
00534
00535 DETATCHSTATUSPTR( status );
00536 RETURN ( status );
00537 }
00538
00539
00540
00541
00542
00543
00544
00545
00546 REAL8
00547 XLALInspiralBissectionLine (
00548 REAL8 tau0,
00549 REAL8 fL,
00550 REAL8 mMin,
00551 REAL8 mMax)
00552 {
00553 REAL8 piFa;
00554 REAL8 tau3_a, tau3_b, M, eta, massSep;
00555
00556
00557 tau3_a = XLALInspiralTau3FromTau0AndEqualMassLine( tau0, fL);
00558
00559
00560 M = mMin + mMax;
00561 eta = (mMin*mMax)/pow(M, 2.0);
00562 massSep = XLALInspiralTau0FromMEta(M, eta, fL);
00563
00564
00565 if (tau0 >= massSep )
00566 {
00567 M = XLALInspiralMFromTau0AndNonEqualMass (tau0, mMin, fL);
00568 eta = mMin*(M-mMin)/ pow(M,2.0);
00569 }
00570 else
00571 {
00572 M = XLALInspiralMFromTau0AndNonEqualMass (tau0, mMax, fL);
00573 eta = mMax*(M-mMax)/ pow(M,2.0);
00574 }
00575
00576 tau3_b = XLALInspiralTau3FromNonEqualMass(M,eta,fL);
00577
00578 return (0.5 * (tau3_a + tau3_b));
00579 }
00580
00581
00582
00583 void
00584 LALPopulateNarrowEdge(LALStatus *status,
00585 InspiralMomentsEtc *moments,
00586 InspiralCell **cell,
00587 INT4 headId,
00588 InspiralTemplate *paramsIn,
00589 HexaGridParam *gridParam,
00590 CellEvolution *cellEvolution,
00591 CellList **cellList,
00592 INT4 flag
00593 )
00594 {
00595 REAL4 dx0, dx1;
00596 REAL4 theta, ctheta,stheta;
00597 INT4 offSpring;
00598 INT4 next, iteration;
00599 REAL4 x_int, y_int,xr_int, yr_int, c,s, dy,theta_min, theta_max, theta_int, a, b, t0, t3;
00600
00601 INITSTATUS( status, "LALPopulateNarrowEdge",
00602 LALINSPIRALHYBRIDHEXAGONALBANKC );
00603 ATTATCHSTATUSPTR( status );
00604
00605
00606
00607
00608 while ( (*cell)[headId].t0 < gridParam->x0Max && (*cell)[headId].t0 > gridParam->x0Min) {
00609
00610 dx0 = (*cell)[headId].dx0/sqrt(2.);
00611 dx1 = (*cell)[headId].dx1/sqrt(2.);
00612 theta = (*cell)[headId].metric.theta;
00613 ctheta = cos(theta);
00614 stheta = sin(theta);
00615 offSpring = cellEvolution->nTemplate;
00616
00617
00618 if ( cellEvolution->nTemplate >= cellEvolution->nTemplateMax){
00619 *cell = (InspiralCell*)
00620 LALRealloc( *cell, sizeof(InspiralCell) * (cellEvolution->nTemplateMax + 1000) );
00621 if ( ! cell ) {
00622 ABORT( status, LALINSPIRALBANKH_EMEM, LALINSPIRALBANKH_MSGEMEM );
00623 }
00624 cellEvolution->nTemplateMax += 1000;
00625 }
00626
00627 next = cellEvolution->nTemplate;
00628
00629 theta_min = 0.+.1 +LAL_PI/2.;
00630 theta_max = 2*LAL_PI-.1+LAL_PI/2.;
00631
00632 theta_min = 0.+.1 ;
00633 theta_max = 2*LAL_PI-.1;
00634
00635
00636
00637
00638 t0 = (*cell)[headId].t0;
00639 t3 = (*cell)[headId].t3;
00640 a = dx0 * sqrt(3.);
00641 b = dx1 * sqrt(3.);
00642 c = cos(theta);
00643 s = sin(theta);
00644
00645
00646 iteration = 1;
00647 while (fabs(theta_max-theta_min)>(.1/180.*LAL_PI) && iteration<20)
00648 {
00649
00650 theta_int = (theta_max + theta_min)/2.;
00651
00652 xr_int = a*cos(theta_int);
00653 yr_int = b*sin(theta_int);
00654
00655
00656
00657 x_int = xr_int *c - yr_int * s +t0;
00658 y_int = xr_int *s + yr_int * c +t3;
00659
00660
00661 dy = y_int - XLALInspiralBissectionLine(x_int, gridParam->fLower, gridParam->mMin,gridParam->mMax);
00662
00663 if (flag==0){
00664 if (dy>0 )
00665 theta_max = theta_int;
00666 else
00667 theta_min = theta_int;
00668 }
00669 else{
00670 if (dy>0 )
00671 theta_min = theta_int;
00672 else
00673 theta_max = theta_int;
00674 }
00675 iteration++;
00676 }
00677
00678
00679
00680 (*cell)[next].t0 = x_int;
00681 (*cell)[next].t3 = y_int;
00682
00683
00684 if ( (*cell)[next].t0 > gridParam->x0Max ){
00685 (*cell)[next].t0 = gridParam->x0Max;
00686 (*cell)[next].t3 = XLALInspiralBissectionLine(gridParam->x0Max, gridParam->fLower, gridParam->mMin,gridParam->mMax);
00687 }
00688
00689 if ( (*cell)[next].t3 > gridParam->x1Max ){
00690 (*cell)[next].t0 = gridParam->x0Max;
00691 (*cell)[next].t3 = XLALInspiralBissectionLine(gridParam->x0Max, gridParam->fLower, gridParam->mMin,gridParam->mMax);
00692 }
00693
00694 if ( (*cell)[next].t0 < gridParam->x0Min ){
00695 (*cell)[next].t0 = gridParam->x0Min;
00696 (*cell)[next].t3 = XLALInspiralBissectionLine(gridParam->x0Min, gridParam->fLower, gridParam->mMin,gridParam->mMax);
00697 }
00698
00699
00700 LALInitHexagonalBank(status->statusPtr, cell, next,
00701 moments, paramsIn, gridParam, cellEvolution, cellList);
00702
00703 cellEvolution->nTemplate++;
00704
00705
00706 (*cell)[next].status = Sterile;
00707 (cellEvolution->fertile)=cellEvolution->fertile-1;
00708 LALListDelete(cellList, next);
00709 headId=next;
00710
00711
00712 }
00713
00714
00715 (*cell)[headId].status = Sterile;
00716 (cellEvolution->fertile)=cellEvolution->fertile-1;
00717 LALListDelete(cellList, headId);
00718 DETATCHSTATUSPTR( status );
00719 RETURN ( status );
00720
00721 }