IPP Software Navigation Tools IPP Links Communication Pan-STARRS Links

Ignore:
Timestamp:
Sep 26, 2017, 7:03:10 PM (9 years ago)
Author:
eugene
Message:

adding the periodogram - floating means

File:
1 edited

Legend:

Unmodified
Added
Removed
  • branches/eam_branches/ohana.20170822/src/opihi/cmd.data/periodogram-fm.c

    r40145 r40146  
    11# include "data.h"
     2# define MIN_VAR 1e-8
     3int periodogram_fm (int argc, char **argv) {
     4 
     5  int N;
    26
    3 int periodogram (int argc, char **argv) {
    4  
    5   int i, N, Npt, Np, NP, VERBOSE;
    6   opihi_flt *tv, *fv;
    7   float minP, maxP, minT, maxT, dTime;
    8   float mean, var, w, tau, P, Pc, Ps, Po;
    9   float C, S, cs, sn, cs2, sn2, ratio;
    10   Vector *time, *flux, *dflux, *power, *period;
    11 
    12   VERBOSE = FALSE;
     7  int VERBOSE = FALSE;
    138  if ((N = get_argument (argc, argv, "-v"))) {
    149    VERBOSE = TRUE;
     
    1712
    1813  if (argc != 8) {
    19     gprint (GP_ERR, "USAGE: periodogram-fm (time) (flux) (dflux) (minP) (maxP) (period) (power)\n");
     14    gprint (GP_ERR, "USAGE: periodogram_fm (time) (flux) (dflux) (minP) (maxP) (period) (power)\n");
    2015    return (FALSE);
    2116  }
     
    2318  // XXX allow dflux to be dropped?
    2419
    25   if ((time  = SelectVector (argv[1], OLDVECTOR, TRUE)) == NULL) return (FALSE);
    26   if ((flux  = SelectVector (argv[2], OLDVECTOR, TRUE)) == NULL) return (FALSE);
    27   if ((dflux = SelectVector (argv[3], OLDVECTOR, TRUE)) == NULL) return (FALSE);
    28   minP = atof(argv[4]);
    29   maxP = atof(argv[5]);
     20  Vector *time, *flux, *dflux, *power, *period;
     21  if ((time   = SelectVector (argv[1], OLDVECTOR, TRUE)) == NULL) return (FALSE);
     22  if ((flux   = SelectVector (argv[2], OLDVECTOR, TRUE)) == NULL) return (FALSE);
     23  if ((dflux  = SelectVector (argv[3], OLDVECTOR, TRUE)) == NULL) return (FALSE);
    3024  if ((period = SelectVector (argv[6], ANYVECTOR, TRUE)) == NULL) return (FALSE);
    3125  if ((power  = SelectVector (argv[7], ANYVECTOR, TRUE)) == NULL) return (FALSE);
     26  double minP = atof(argv[4]);
     27  double maxP = atof(argv[5]);
    3228
    3329  REQUIRE_VECTOR_FLT (time, FALSE);
    3430  REQUIRE_VECTOR_FLT (flux, FALSE);
     31  REQUIRE_VECTOR_FLT (dflux, FALSE);
    3532
    36   /* find the max baseline, mean, and variance */
    37   minT = maxT = time[0].elements.Flt[0];
    38   Npt = time[0].Nelements;
    39   tv = time[0].elements.Flt;
    40   fv = flux[0].elements.Flt;
    41   mean = var = 0;
    42   for (i = 0; i < Npt; i++, tv++, fv++) {
     33  /* find the max baseline, sum the inverse variances */
     34  double minT = time[0].elements.Flt[0];
     35  double maxT = time[0].elements.Flt[0];
     36  opihi_flt Weight = 0;
     37  int Npt = time[0].Nelements;
     38
     39  opihi_flt *tv =  time[0].elements.Flt;
     40  opihi_flt *df = dflux[0].elements.Flt;
     41  for (int i = 0; i < Npt; i++, tv++, df++) {
    4342    minT = MIN (minT, *tv);
    4443    maxT = MAX (maxT, *tv);
    45     mean += *fv;
     44    // skip points with 0.0 error? or add minimum variance?
     45    Weight += 1.0 / (SQ(*df) + MIN_VAR); // MIN_VAR : added in quadrature to avoid Inf (XXX make this a user parameter?)
    4646  }
    47   mean = mean / Npt;
    48   fv = flux[0].elements.Flt;
    49   for (i = 0; i < Npt; i++, fv++) {
    50     var += SQ(*fv - mean);
    51   }
    52   var = var / (Npt - 1);
    5347
    54   if (VERBOSE) gprint (GP_ERR, "mean: %f, var: %f, minT: %f, maxT: %f\n", mean, var, minT, maxT);
    55 
    56   dTime = maxT - minT;
     48  double WeightInv = 1.0 / Weight;
     49  double dTime = maxT - minT;
    5750  if (dTime == 0) {
    5851    gprint (GP_ERR, "ERROR: time range is zero\n");
     
    6053  }
    6154
    62   Np = 0;
    63   NP = 100;
     55  int Np = 0;
     56  int NP = 100;
    6457  ResetVector (power,  OPIHI_FLT, NP);
    6558  ResetVector (period, OPIHI_FLT, NP);
     
    7063
    7164  // XXX consider choice of period or frequency step
    72   P = minP;
    73   while (P < maxP) {
    74     w = 2*M_PI/P;
     65  double P = minP;
     66  while (P <= maxP) {
     67    double w = 2*M_PI/P;
    7568   
    7669    /* find the period offset tau  */
     
    7871    df = dflux[0].elements.Flt;
    7972
    80     cs = sn = cs2 = sn2 = 0;
     73    double cs = 0.0, sn = 0.0, sn2 = 0.0, cs2 = 0.0;
    8174
    82     for (i = 0; i < Npt; i++, tv++) {
    83       opihi_flt wt =
    84       cs += cos (*tv*w*2);
    85       sn += sin (*tv*2*2);
     75    for (int i = 0; i < Npt; i++, tv++, df++) {
     76      opihi_flt wt = WeightInv / (SQ(*df) + MIN_VAR);
     77      cs  += wt*cos (*tv*w);
     78      sn  += wt*sin (*tv*w);
     79      cs2 += wt*cos (*tv*w*2);
     80      sn2 += wt*sin (*tv*w*2);
    8681    }
    87     tau = 0.5*atan2 (sn, cs) / w;
     82    double ytan = sn2 - 2*cs*sn;
     83    double xtan = cs2 - (SQ(cs) - SQ(sn));
     84    double tau = 0.5*atan2 (ytan, xtan) / w;
    8885     
    8986    /* find the power at this period */
    9087    tv = time[0].elements.Flt;
    91     fv = flux[0].elements.Flt;
    92     cs = sn = cs2 = sn2 = 0;
    93     for (i = 0; i < Npt; i++, tv++, fv++) {
    94       C = cos (w*(*tv-tau));
    95       S = sin (w*(*tv-tau));
    96       // C = cos (w**tv);
    97       // S = sin (w**tv);
    98       cs += (*fv - mean) * C;
    99       sn += (*fv - mean) * S;
    100       cs2 += SQ(C);
    101       sn2 += SQ(S);
     88    df = dflux[0].elements.Flt;
     89    opihi_flt *fv = flux[0].elements.Flt;
     90
     91    // YY = YY_s - Y_s*Y_s
     92    // CC = CC_s - C_s*C_s
     93    // SS = SS_s - S_s*S_s
     94    // YC = YC_s - Y_s*C_s
     95    // YS = YS_s - Y_s*S_s
     96   
     97    double YY_s = 0.0, CC_s = 0.0, SS_s = 0.0, YC_s = 0.0, YS_s = 0.0;
     98    double Y_s = 0.0, C_s = 0.0, S_s = 0.0;
     99    for (int i = 0; i < Npt; i++, tv++, fv++, df++) {
     100      opihi_flt wt = WeightInv / (SQ(*df) + MIN_VAR);
     101      cs = cos (w*(*tv-tau));
     102      sn = sin (w*(*tv-tau));
     103
     104      double wtf = *fv*wt;
     105      Y_s += wtf;
     106      C_s += wt*cs;
     107      S_s += wt*sn;
     108
     109      YY_s += wtf*(*fv);
     110      YC_s += wtf*cs;
     111      YS_s += wtf*sn;
     112
     113      CC_s += wt*cs*cs;
     114      SS_s += wt*sn*sn;
    102115    }
    103     Pc = SQ(cs) / cs2;
    104     Ps = SQ(sn) / sn2;
    105     Po = (Pc + Ps) / (2*var);
     116    double YY = YY_s - SQ(Y_s);
     117    double YC = YC_s - Y_s*C_s;
     118    double YS = YS_s - Y_s*S_s;
     119    double CC = CC_s - SQ(C_s);
     120    double SS = SS_s - SQ(S_s);
     121
     122    double Pa = SQ(YC) / CC;
     123    double Pb = SQ(YS) / SS;
     124    double Po = (Pa + Pb) / YY;
    106125
    107126    power[0].elements.Flt[Np] = Po;
     
    114133    }
    115134
    116     ratio = 1 + 0.1*P/dTime;
     135    double ratio = 1 + 0.1*P/dTime;
    117136
    118137    if (VERBOSE) gprint (GP_ERR, "tau: %f, P: %f, ratio: %f, dTime: %f, nextP: %f\n", tau, P, ratio, dTime, P*ratio);
Note: See TracChangeset for help on using the changeset viewer.