public void TestSetItemOutOfRange() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer <int> target = new CPointer <int>(array); target[100] = 12; }
public void TestGetItemOutOfRange() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer <int> target = new CPointer <int>(array); Assert.AreEqual(0, target[100]); }
public void TestDecrement() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer<int> target = new CPointer<int>(array, 5); Assert.AreEqual(5, target[0]); target--; Assert.AreEqual(4, target[0]); }
public void TestAdditionWithInt() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer<int> target = new CPointer<int>(array); Assert.AreEqual(0, target[0]); target = target + 2; Assert.AreEqual(2, target[0]); }
public void TestIncrement() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer <int> target = new CPointer <int>(array); Assert.Equal(0, target[0]); target++; Assert.Equal(1, target[0]); }
public void TestAdditionWithInt() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer <int> target = new CPointer <int>(array); Assert.Equal(0, target[0]); target = target + 2; Assert.Equal(2, target[0]); }
public void TestSubstractionWithInt() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer <int> target = new CPointer <int>(array, 5); Assert.Equal(5, target[0]); target = target - 2; Assert.Equal(3, target[0]); }
public void TestEquals() { int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; CPointer <int> target = new CPointer <int>(array); Assert.False(target.Equals(null)); Assert.False(target.Equals(5)); Assert.True(target.Equals(array)); Assert.True(target.Equals(new CPointer <int>(array))); Assert.False(target.Equals(new CPointer <int>(array, 5))); }
public void TestEqualityWithArray() { int[] array1 = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; int[] array2 = new int[] { 9, 8, 7, 6, 5, 4, 3, 2, 1 }; CPointer<int> target = new CPointer<int>(array1); Assert.IsTrue(array1 == target); Assert.IsTrue(target == array1); Assert.IsFalse(array2 == target); Assert.IsFalse(target == array2); Assert.IsFalse(array1 != target); Assert.IsFalse(target != array1); Assert.IsTrue(array2 != target); Assert.IsTrue(target != array2); }
/* * this entry obtains the constants from the ephemeris file * call state to initialize the ephemeris and read in the constants */ int read_const_jpl(CPointer <double> ss, ref string serr) { int i, retc; retc = state(0.0, null, false, null, null, null, ref serr); if (retc != SwissEph.OK) { return(retc); } for (i = 0; i < 3; i++) { ss[i] = js.eh_ss[i]; } #if DEBUG_DO_SHOW {
public void TestCreate() { CPointer<int> target = new CPointer<int>(); Assert.AreEqual(true, target.IsNull); Assert.AreEqual(0, target.Length); int[] array = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; target = new CPointer<int>(array); Assert.AreEqual(false, target.IsNull); Assert.AreEqual(10, target.Length); target = new CPointer<int>(array, 5); Assert.AreEqual(false, target.IsNull); Assert.AreEqual(5, target.Length); }
public void TestEquality() { int[] array1 = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9 }; int[] array2 = new int[] { 9, 8, 7, 6, 5, 4, 3, 2, 1 }; CPointer<int> target1 = new CPointer<int>(array1); CPointer<int> target2 = new CPointer<int>(array2); CPointer<int> target3 = new CPointer<int>(array1, 5); CPointer<int> target4 = new CPointer<int>(array2, 5); Assert.IsTrue(target1 == new CPointer<int>(array1)); Assert.IsFalse(target1 != new CPointer<int>(array1)); Assert.IsFalse(target2 == target1); Assert.IsTrue(target2 != target1); Assert.IsFalse(target3 == target1); Assert.IsTrue(target3 != target1); Assert.IsFalse(target4 == target1); Assert.IsTrue(target4 != target1); }
/* * evaluates derivative of chebyshev series, see echeb */ public double swi_edcheb(double x, CPointer<double> coef, int ncf) { double bjpl, xjpl; int j; double x2, bf, bj, dj, xj, bjp2, xjp2; x2 = x * 2.0; bf = 0.0; /* dummy assign to silence gcc warning */ bj = 0.0; /* dummy assign to silence gcc warning */ xjp2 = 0.0; xjpl = 0.0; bjp2 = 0.0; bjpl = 0.0; for (j = ncf - 1; j >= 1; j--) { dj = (double)(j + j); xj = coef[j] * dj + xjp2; bj = x2 * bjpl - bjp2 + xj; bf = bjp2; bjp2 = bjpl; bjpl = bj; xjp2 = xjpl; xjpl = xj; } return (bj - bf) * 0.5; }
/* Evaluates a given chebyshev series coef[0..ncf-1] * with ncf terms at x in [-1,1]. Communications of the ACM, algorithm 446, * April 1973 (vol. 16 no.4) by Dr. Roger Broucke. */ public double swi_echeb(double x, CPointer<double> coef, int ncf) { int j; double x2, br, brp2, brpp; x2 = x * 2.0; br = 0.0; brp2 = 0.0; /* dummy assign to silence gcc warning */ brpp = 0.0; for (j = ncf - 1; j >= 0; j--) { brp2 = brpp; brpp = br; br = x2 * brpp - brp2 + coef[j]; } return (br - brp2) * 0.5; }
public double dot_prod(CPointer <double> x, CPointer <double> y) { return(x[0] * y[0] + x[1] * y[1] + x[2] * y[2]); }
public void TestGetItemNullReferenceException() { CPointer <int> target = new CPointer <int>(); Assert.AreEqual(0.0, target[0]); }
double bessel(CPointer<double> v, int n, double t) { int i, iy, k; double ans, p, B; double[] d = new double[6]; if (t <= 0) { ans = v[0]; goto done; } if (t >= n - 1) { ans = v[n - 1]; goto done; } p = Math.Floor(t); iy = (int)t; /* Zeroth order estimate is value at start of year */ ans = v[iy]; k = iy + 1; if (k >= n) goto done; /* The fraction of tabulation interval */ p = t - p; ans += p * (v[k] - v[iy]); if ((iy - 1 < 0) || (iy + 2 >= n)) goto done; /* can't do second differences */ /* Make table of first differences */ k = iy - 2; for (i = 0; i < 5; i++) { if ((k < 0) || (k + 1 >= n)) d[i] = 0; else d[i] = v[k + 1] - v[k]; k += 1; } /* Compute second differences */ for (i = 0; i < 4; i++) d[i] = d[i + 1] - d[i]; B = 0.25 * p * (p - 1.0); ans += B * (d[1] + d[2]); #if DEMO printf("B %.4lf, ans %.4lf\n", B, ans); #endif if (iy + 2 >= n) goto done; /* Compute third differences */ for (i = 0; i < 3; i++) d[i] = d[i + 1] - d[i]; B = 2.0 * B / 3.0; ans += (p - 0.5) * B * d[1]; #if DEMO printf("B %.4lf, ans %.4lf\n", B * (p - 0.5), ans); #endif if ((iy - 2 < 0) || (iy + 3 > n)) goto done; /* Compute fourth differences */ for (i = 0; i < 2; i++) d[i] = d[i + 1] - d[i]; B = 0.125 * B * (p + 1.0) * (p - 2.0); ans += B * (d[0] + d[1]); #if DEMO printf("B %.4lf, ans %.4lf\n", B, ans); #endif done: return ans; }
/* conversion of position and speed * from polar (l[6]) to cartesian coordinates (x[6]) * x = l is allowed * explanation s. swi_cartpol_sp() */ public void swi_polcart_sp(CPointer<double> l, CPointer<double> x) { double sinlon, coslon, sinlat, coslat; double[] xx = new double[6]; double rxy, rxyz; /* zero speed */ if (l[3] == 0 && l[4] == 0 && l[5] == 0) { x[3] = x[4] = x[5] = 0; swi_polcart((double[])l, (double[])x); return; } /* position */ coslon = Math.Cos(l[0]); sinlon = Math.Sin(l[0]); coslat = Math.Cos(l[1]); sinlat = Math.Sin(l[1]); xx[0] = l[2] * coslat * coslon; xx[1] = l[2] * coslat * sinlon; xx[2] = l[2] * sinlat; /* speed; explanation s. swi_cartpol_sp(), same method the other way round*/ rxyz = l[2]; rxy = Math.Sqrt(xx[0] * xx[0] + xx[1] * xx[1]); xx[5] = l[5]; xx[4] = l[4] * rxyz; x[5] = sinlat * xx[5] + coslat * xx[4]; /* speed z */ xx[3] = coslat * xx[5] - sinlat * xx[4]; xx[4] = l[3] * rxy; x[3] = coslon * xx[3] - sinlon * xx[4]; /* speed x */ x[4] = sinlon * xx[3] + coslon * xx[4]; /* speed y */ x[0] = xx[0]; /* return position */ x[1] = xx[1]; x[2] = xx[2]; }
public int swi_nutation(double J, Int32 iflag, CPointer<double> nutlo) { int n; double dpsi, deps, J2; int nut_model = swed.astro_models[SwissEph.SE_MODEL_NUT]; int jplhor_model = swed.astro_models[SwissEph.SE_MODEL_JPLHOR_MODE]; int jplhora_model = swed.astro_models[SwissEph.SE_MODEL_JPLHORA_MODE]; if (nut_model == 0) nut_model = SwissEph.SEMOD_NUT_DEFAULT; if (jplhor_model == 0) jplhor_model = SwissEph.SEMOD_JPLHOR_DEFAULT; if (jplhora_model == 0) jplhora_model = SwissEph.SEMOD_JPLHORA_DEFAULT; /*if ((iflag & SEFLG_JPLHOR) && (jplhor_model & SEMOD_JPLHOR_DAILY_DATA)) {*/ if ((iflag & SwissEph.SEFLG_JPLHOR)!=0/* && INCLUDE_CODE_FOR_DPSI_DEPS_IAU1980*/) { swi_nutation_iau1980(J, nutlo); } else if (nut_model == SwissEph.SEMOD_NUT_IAU_1980 || nut_model == SwissEph.SEMOD_NUT_IAU_CORR_1987) { swi_nutation_iau1980(J, nutlo); } else if (nut_model == SwissEph.SEMOD_NUT_IAU_2000A || nut_model == SwissEph.SEMOD_NUT_IAU_2000B) { swi_nutation_iau2000ab(J, nutlo); /*if ((iflag & SEFLG_JPLHOR_APPROX) && FRAME_BIAS_APPROX_HORIZONS) {*/ /*if ((iflag & SEFLG_JPLHOR_APPROX) && !APPROXIMATE_HORIZONS_ASTRODIENST) {*/ if ((iflag & SwissEph.SEFLG_JPLHOR_APPROX)!=0 && jplhora_model != SwissEph.SEMOD_JPLHORA_1) { nutlo[0] += -41.7750 / 3600.0 / 1000.0 * SwissEph.DEGTORAD; nutlo[1] += -6.8192 / 3600.0 / 1000.0 * SwissEph.DEGTORAD; } } if ((iflag & SwissEph.SEFLG_JPLHOR) != 0/* && INCLUDE_CODE_FOR_DPSI_DEPS_IAU1980*/) { n = (int)(swed.eop_tjd_end - swed.eop_tjd_beg + 0.000001); J2 = J; if (J < swed.eop_tjd_beg_horizons) J2 = swed.eop_tjd_beg_horizons; dpsi = bessel(swed.dpsi, n + 1, J2 - swed.eop_tjd_beg); deps = bessel(swed.deps, n + 1, J2 - swed.eop_tjd_beg); nutlo[0] += dpsi / 3600.0 * SwissEph.DEGTORAD; nutlo[1] += deps / 3600.0 * SwissEph.DEGTORAD; //#if 0 // printf("tjd=%f, dpsi=%f, deps=%f\n", J, dpsi * 1000, deps * 1000); //#endif } return SwissEph.OK; }
/// <summary> /// swe_houses_ex() /// </summary> public int swe_houses_ex(double tjd_ut, double geolat, double geolon, CPointer <double> hcusps, CPointer <double> ascmc) { CheckInitialized(); return(SwissEph.swe_houses_ex(tjd_ut, _SwissFlag, geolat, geolon, _Hsys, hcusps, ascmc)); }
serr = C.sprintf("JPL ephemeris file does not provide valid ksize (%d)", ksize);/**/ return(Sweph.NOT_AVAILABLE); } return(ksize); } /* * This subroutine reads the jpl planetary ephemeris * and gives the position and velocity of the point 'ntarg' * with respect to 'ncent'. * calling sequence parameters: * et = d.p. julian ephemeris date at which interpolation * is wanted. * ** note the entry dpleph for a doubly-dimensioned time ** * the reason for this option is discussed in the * subroutine state * ntarg = integer number of 'target' point. * ncent = integer number of center point. * the numbering convention for 'ntarg' and 'ncent' is: * 0 = mercury 7 = neptune * 1 = venus 8 = pluto * 2 = earth 9 = moon * 3 = mars 10 = sun * 4 = jupiter 11 = solar-system barycenter * 5 = saturn 12 = earth-moon barycenter * 6 = uranus 13 = nutations (longitude and obliq) * 14 = librations, if on eph file * (if nutations are wanted, set ntarg = 13. for librations, * set ntarg = 14. set ncent=0.) * rrd = output 6-word d.p. array containing position and velocity * of point 'ntarg' relative to 'ncent'. the units are au and * au/day. for librations the units are radians and radians * per day. in the case of nutations the first four words of * rrd will be set to nutations and rates, having units of * radians and radians/day. * The option is available to have the units in km and km/sec. * For this, set do_km=TRUE (default FALSE). */ public int swi_pleph(double et, int ntarg, int ncent, CPointer <double> rrd, ref string serr) { int i, retc; Int32[] list = new Int32[12]; double[] pv = js.pv; double[] pvsun = js.pvsun; for (i = 0; i < 6; ++i) { rrd[i] = 0.0; } if (ntarg == ncent) { return(0); } for (i = 0; i < 12; ++i) { list[i] = 0; } /* check for nutation call */ if (ntarg == J_NUT) { if (js.eh_ipt[34] > 0) { list[10] = 2; return(state(et, list, false, pv, pvsun, rrd, ref serr)); } else { serr = "No nutations on the JPL ephemeris file;"; return(Sweph.NOT_AVAILABLE); } } if (ntarg == J_LIB) { if (js.eh_ipt[37] > 0) { list[11] = 2; if ((retc = state(et, list, false, pv, pvsun, rrd, ref serr)) != SwissEph.OK) { return(retc); } for (i = 0; i < 6; ++i) { rrd[i] = pv[i + 60]; } return(0); } else { serr = C.sprintf("No librations on the ephemeris file;"); return(Sweph.NOT_AVAILABLE); } } /* set up proper entries in 'list' array for state call */ if (ntarg < J_SUN) { list[ntarg] = 2; } if (ntarg == J_MOON) /* Mooon needs Earth */ { list[J_EARTH] = 2; } if (ntarg == J_EARTH) /* Earth needs Moon */ { list[J_MOON] = 2; } if (ntarg == J_EMB) /* EMB needs Earth */ { list[J_EARTH] = 2; } if (ncent < J_SUN) { list[ncent] = 2; } if (ncent == J_MOON) /* Mooon needs Earth */ { list[J_EARTH] = 2; } if (ncent == J_EARTH) /* Earth needs Moon */ { list[J_MOON] = 2; } if (ncent == J_EMB) /* EMB needs Earth */ { list[J_EARTH] = 2; } if ((retc = state(et, list, true, pv, pvsun, rrd, ref serr)) != SwissEph.OK) { return(retc); } if (ntarg == J_SUN || ncent == J_SUN) { for (i = 0; i < 6; ++i) { pv[i + 6 * J_SUN] = pvsun[i]; } } if (ntarg == J_SBARY || ncent == J_SBARY) { for (i = 0; i < 6; ++i) { pv[i + 6 * J_SBARY] = 0.0; } } if (ntarg == J_EMB || ncent == J_EMB) { for (i = 0; i < 6; ++i) { pv[i + 6 * J_EMB] = pv[i + 6 * J_EARTH]; } } if ((ntarg == J_EARTH && ncent == J_MOON) || (ntarg == J_MOON && ncent == J_EARTH)) { for (i = 0; i < 6; ++i) { pv[i + 6 * J_EARTH] = 0.0; } } else { if (list[J_EARTH] == 2) { for (i = 0; i < 6; ++i) { pv[i + 6 * J_EARTH] -= pv[i + 6 * J_MOON] / (js.eh_emrat + 1.0); } } if (list[J_MOON] == 2) { for (i = 0; i < 6; ++i) { pv[i + 6 * J_MOON] += pv[i + 6 * J_EARTH]; } } } for (i = 0; i < 6; ++i) { rrd[i] = pv[i + ntarg * 6] - pv[i + ncent * 6]; } return(SwissEph.OK); }
/* Moshier ephemeris. * computes heliocentric cartesian equatorial coordinates of * equinox 2000 * for earth and a planet * tjd julian day * ipli internal SWEPH planet number * xp array of 6 doubles for planet's position and speed * xe earth's * serr error string */ public int swi_moshplan(double tjd, int ipli, bool do_save, CPointer <double> xpret, CPointer <double> xeret, ref string serr) { int i; bool do_earth = false; double[] dx = new double[3], x2 = new double[3], xxe = new double[6], xxp = new double[6]; double[] xp, xe; double dt; string s = String.Empty; int iplm = pnoint2msh[ipli]; Sweph.plan_data pdp = SE.Sweph.swed.pldat[ipli]; Sweph.plan_data pedp = SE.Sweph.swed.pldat[Sweph.SEI_EARTH]; double seps2000 = SE.Sweph.swed.oec2000.seps; double ceps2000 = SE.Sweph.swed.oec2000.ceps; if (do_save) { xp = pdp.x; xe = pedp.x; } else { xp = xxp; xe = xxe; } if (do_save || ipli == Sweph.SEI_EARTH || xeret != null) { do_earth = true; } /* tjd beyond ephemeris limits, give some margin for spped at edge */ if (tjd < Sweph.MOSHPLEPH_START - 0.3 || tjd > Sweph.MOSHPLEPH_END + 0.3) { s = C.sprintf("jd %f outside Moshier planet range %.2f .. %.2f ", tjd, Sweph.MOSHPLEPH_START, Sweph.MOSHPLEPH_END); serr = (serr ?? String.Empty) + s; return(SwissEph.ERR); } /* earth, for geocentric position */ if (do_earth) { if (tjd == pedp.teval && pedp.iephe == SwissEph.SEFLG_MOSEPH) { xe = pedp.x; } else { /* emb */ swi_moshplan2(tjd, pnoint2msh[Sweph.SEI_EMB], xe); /* emb hel. ecl. 2000 polar */ SE.SwephLib.swi_polcart(xe, xe); /* to cartesian */ SE.SwephLib.swi_coortrf2(xe, xe, -seps2000, ceps2000); /* and equator 2000 */ embofs_mosh(tjd, xe); /* emb -> earth */ if (do_save) { pedp.teval = tjd; pedp.xflgs = -1; pedp.iephe = SwissEph.SEFLG_MOSEPH; } /* one more position for speed. */ swi_moshplan2(tjd - Sweph.PLAN_SPEED_INTV, pnoint2msh[Sweph.SEI_EMB], x2); SE.SwephLib.swi_polcart(x2, x2); SE.SwephLib.swi_coortrf2(x2, x2, -seps2000, ceps2000); embofs_mosh(tjd - Sweph.PLAN_SPEED_INTV, x2);/**/ for (i = 0; i <= 2; i++) { dx[i] = (xe[i] - x2[i]) / Sweph.PLAN_SPEED_INTV; } /* store speed */ for (i = 0; i <= 2; i++) { xe[i + 3] = dx[i]; } } if (xeret != null) { for (i = 0; i <= 5; i++) { xeret[i] = xe[i]; } } } /* earth is the planet wanted */ if (ipli == Sweph.SEI_EARTH) { xp = xe; } else { /* other planet */ /* if planet has already been computed, return */ if (tjd == pdp.teval && pdp.iephe == SwissEph.SEFLG_MOSEPH) { xp = pdp.x; } else { swi_moshplan2(tjd, iplm, xp); SE.SwephLib.swi_polcart(xp, xp); SE.SwephLib.swi_coortrf2(xp, xp, -seps2000, ceps2000); if (do_save) { pdp.teval = tjd;/**/ pdp.xflgs = -1; pdp.iephe = SwissEph.SEFLG_MOSEPH; } /* one more position for speed. * the following dt gives good speed for light-time correction */ //#if 0 // for (i = 0; i <= 2; i++) //dx[i] = xp[i] - pedp.x[i]; // dt = LIGHTTIME_AUNIT * Math.Sqrt(square_sum(dx)); //#endif dt = Sweph.PLAN_SPEED_INTV; swi_moshplan2(tjd - dt, iplm, x2); SE.SwephLib.swi_polcart(x2, x2); SE.SwephLib.swi_coortrf2(x2, x2, -seps2000, ceps2000); for (i = 0; i <= 2; i++) { dx[i] = (xp[i] - x2[i]) / dt; } /* store speed */ for (i = 0; i <= 2; i++) { xp[i + 3] = dx[i]; } } if (xpret != null) { for (i = 0; i <= 5; i++) { xpret[i] = xp[i]; } } } return(SwissEph.OK); } /* Prepare lookup table of sin and cos ( i*Lj ) * for required multiple angles */ void plan_sscc(int k, double arg, int n) { double cu, su, cv, sv, s; int i; su = Math.Sin(arg); cu = Math.Cos(arg); plan_ss[k, 0] = su; /* sin(L) */ plan_cc[k, 0] = cu; /* cos(L) */ sv = 2.0 * su * cu; cv = cu * cu - su * su; plan_ss[k, 1] = sv; /* sin(2L) */ plan_cc[k, 1] = cv; for (i = 2; i < n; i++) { s = su * cv + cu * sv; cv = cu * cv - su * sv; sv = s; plan_ss[k, i] = sv; /* sin( i+1 L ) */ plan_cc[k, i] = cv; } } /* Adjust position from Earth-Moon barycenter to Earth * * J = Julian day number * xemb = rectangular equatorial coordinates of Earth */ void embofs_mosh(double tjd, CPointer <double> xemb) { double T, M, a, L, B, p; double smp, cmp, s2mp, c2mp, s2d, c2d, sf, cf; double s2f, sx, cx; double[] xyz = new double[6]; double seps = SE.Sweph.swed.oec.seps; double ceps = SE.Sweph.swed.oec.ceps; int i; /* Short series for position of the Moon */ T = (tjd - Sweph.J1900) / 36525.0; /* Mean anomaly of moon (MP) */ a = SE.swe_degnorm(((1.44e-5 * T + 0.009192) * T + 477198.8491) * T + 296.104608); a *= SwissEph.DEGTORAD; smp = Math.Sin(a); cmp = Math.Cos(a); s2mp = 2.0 * smp * cmp; /* sin(2MP) */ c2mp = cmp * cmp - smp * smp; /* cos(2MP) */ /* Mean elongation of moon (D) */ a = SE.swe_degnorm(((1.9e-6 * T - 0.001436) * T + 445267.1142) * T + 350.737486); a = 2.0 * SwissEph.DEGTORAD * a; s2d = Math.Sin(a); c2d = Math.Cos(a); /* Mean distance of moon from its ascending node (F) */ a = SE.swe_degnorm(((-3.0e-7 * T - 0.003211) * T + 483202.0251) * T + 11.250889); a *= SwissEph.DEGTORAD; sf = Math.Sin(a); cf = Math.Cos(a); s2f = 2.0 * sf * cf; /* sin(2F) */ sx = s2d * cmp - c2d * smp; /* sin(2D - MP) */ cx = c2d * cmp + s2d * smp; /* cos(2D - MP) */ /* Mean longitude of moon (LP) */ L = ((1.9e-6 * T - 0.001133) * T + 481267.8831) * T + 270.434164; /* Mean anomaly of sun (M) */ M = SE.swe_degnorm(((-3.3e-6 * T - 1.50e-4) * T + 35999.0498) * T + 358.475833); /* Ecliptic longitude of the moon */ L = L + 6.288750 * smp + 1.274018 * sx + 0.658309 * s2d + 0.213616 * s2mp - 0.185596 * Math.Sin(SwissEph.DEGTORAD * M) - 0.114336 * s2f; /* Ecliptic latitude of the moon */ a = smp * cf; sx = cmp * sf; B = 5.128189 * sf + 0.280606 * (a + sx) /* sin(MP+F) */ + 0.277693 * (a - sx) /* sin(MP-F) */ + 0.173238 * (s2d * cf - c2d * sf); /* sin(2D-F) */ B *= SwissEph.DEGTORAD; /* Parallax of the moon */ p = 0.950724 + 0.051818 * cmp + 0.009531 * cx + 0.007843 * c2d + 0.002824 * c2mp; p *= SwissEph.DEGTORAD; /* Elongation of Moon from Sun */ L = SE.swe_degnorm(L); L *= SwissEph.DEGTORAD; /* Distance in au */ a = 4.263523e-5 / Math.Sin(p); /* Convert to rectangular ecliptic coordinates */ xyz[0] = L; xyz[1] = B; xyz[2] = a; SE.SwephLib.swi_polcart(xyz, xyz); /* Convert to equatorial */ SE.SwephLib.swi_coortrf2(xyz, xyz, -seps, ceps); /* Precess to equinox of J2000.0 */ SE.SwephLib.swi_precess(xyz, tjd, 0, Sweph.J_TO_J2000);/**/ /* now emb -> earth */ for (i = 0; i <= 2; i++) { xemb[i] -= xyz[i] / (Sweph.EARTH_MOON_MRAT + 1.0); } }
//static void sscc (int k, double arg, int n); int swi_moshplan2(double J, int iplm, CPointer <double> pobj) { int i, j, k, m, k1, ip, np, nt; sbyte[] p; int pidx; double[] plarr, pbarr, prarr; int plidx, pbidx, pridx; double su, cu, sv, cv, T; double t, sl, sb, sr; Sweph.plantbl plan = planets[iplm]; T = (J - Sweph.J2000) / TIMESCALE; /* Calculate sin( i*MM ), etc. for needed multiple angles. */ for (i = 0; i < 9; i++) { if ((j = plan.max_harmonic[i]) > 0) { sr = (mods3600(freqs[i] * T) + phases[i]) * Sweph.STR; plan_sscc(i, sr, j); } } /* Point to start of table of arguments. */ p = plan.arg_tbl; pidx = 0; /* Point to tabulated cosine and sine amplitudes. */ plarr = plan.lon_tbl; plidx = 0; pbarr = plan.lat_tbl; pbidx = 0; prarr = plan.rad_tbl; pridx = 0; sl = 0.0; sb = 0.0; sr = 0.0; for (; ;) { /* argument of sine and cosine */ /* Number of periodic arguments. */ np = p[pidx++]; if (np < 0) { break; } if (np == 0) /* It is a polynomial term. */ { nt = p[pidx++]; /* Longitude polynomial. */ cu = plarr[plidx++]; for (ip = 0; ip < nt; ip++) { cu = cu * T + plarr[plidx++]; } sl += mods3600(cu); /* Latitude polynomial. */ cu = pbarr[pbidx++]; for (ip = 0; ip < nt; ip++) { cu = cu * T + pbarr[pbidx++]; } sb += cu; /* Radius polynomial. */ cu = prarr[pridx++]; for (ip = 0; ip < nt; ip++) { cu = cu * T + prarr[pridx++]; } sr += cu; continue; } k1 = 0; cv = 0.0; sv = 0.0; for (ip = 0; ip < np; ip++) { /* What harmonic. */ j = p[pidx++]; /* Which planet. */ m = p[pidx++] - 1; if (j != 0) { k = j; if (j < 0) { k = -k; } k -= 1; su = plan_ss[m, k]; /* sin(k*angle) */ if (j < 0) { su = -su; } cu = plan_cc[m, k]; if (k1 == 0) /* set first angle */ { sv = su; cv = cu; k1 = 1; } else /* combine angles */ { t = su * cv + cu * sv; cv = cu * cv - su * sv; sv = t; } } } /* Highest power of T. */ nt = p[pidx++]; /* Longitude. */ cu = plarr[plidx++]; su = plarr[plidx++]; for (ip = 0; ip < nt; ip++) { cu = cu * T + plarr[plidx++]; su = su * T + plarr[plidx++]; } sl += cu * cv + su * sv; /* Latitiude. */ cu = pbarr[pbidx++]; su = pbarr[pbidx++]; for (ip = 0; ip < nt; ip++) { cu = cu * T + pbarr[pbidx++]; su = su * T + pbarr[pbidx++]; } sb += cu * cv + su * sv; /* Radius. */ cu = prarr[pridx++]; su = prarr[pridx++]; for (ip = 0; ip < nt; ip++) { cu = cu * T + prarr[pridx++]; su = su * T + prarr[pridx++]; } sr += cu * cv + su * sv; } pobj[0] = Sweph.STR * sl; pobj[1] = Sweph.STR * sb; pobj[2] = Sweph.STR * plan.distance * sr + plan.distance; return(SwissEph.OK); }
public void TestSetItemNullReferenceException() { CPointer <int> target = new CPointer <int>(); target[0] = 12; }
int interp(CPointer <double> buf, double t, double intv, Int32 ncfin, Int32 ncmin, Int32 nain, Int32 ifl, CPointer <double> pv) { /* Initialized data */ double[] pc = js.pc; double[] vc = js.vc; double[] ac = js.ac; double[] jc = js.jc; int ncf = (int)ncfin; int ncm = (int)ncmin; int na = (int)nain; /* Local variables */ double temp; int i, j, ni; double tc; double dt1, bma; double bma2, bma3; /* | get correct sub-interval number for this set of coefficients and then | get normalized chebyshev time within that subinterval. */ if (t >= 0) { dt1 = Math.Floor(t); } else { dt1 = -Math.Floor(-t); } temp = na * t; ni = (int)(temp - dt1); /* tc is the normalized chebyshev time (-1 <= tc <= 1) */ tc = ((temp % 1.0) + dt1) * 2.0 - 1.0; /* * check to see whether chebyshev time has changed, * and compute new polynomial values if it has. * (the element pc(2) is the value of t1(tc) and hence * contains the value of tc on the previous call.) */ if (tc != pc[1]) { np = 2; nv = 3; nac = 4; njk = 5; pc[1] = tc; twot = tc + tc; } /* * be sure that at least 'ncf' polynomials have been evaluated * and are stored in the array 'pc'. */ if (np < ncf) { for (i = np; i < ncf; ++i) { pc[i] = twot * pc[i - 1] - pc[i - 2]; } np = ncf; } /* interpolate to get position for each component */ for (i = 0; i < ncm; ++i) { pv[i] = 0.0; for (j = ncf - 1; j >= 0; --j) { pv[i] += pc[j] * buf[j + (i + ni * ncm) * ncf]; } } if (ifl <= 1) { return(0); } /* * if velocity interpolation is wanted, be sure enough * derivative polynomials have been generated and stored. */ bma = (na + na) / intv; vc[2] = twot + twot; if (nv < ncf) { for (i = nv; i < ncf; ++i) { vc[i] = twot * vc[i - 1] + pc[i - 1] + pc[i - 1] - vc[i - 2]; } nv = ncf; } /* interpolate to get velocity for each component */ for (i = 0; i < ncm; ++i) { pv[i + ncm] = 0.0; for (j = ncf - 1; j >= 1; --j) { pv[i + ncm] += vc[j] * buf[j + (i + ni * ncm) * ncf]; } pv[i + ncm] *= bma; } if (ifl == 2) { return(0); } /* check acceleration polynomial values, and */ /* re-do if necessary */ bma2 = bma * bma; ac[3] = pc[1] * 24.0; if (nac < ncf) { nac = ncf; for (i = nac; i < ncf; ++i) { ac[i] = twot * ac[i - 1] + vc[i - 1] * 4.0 - ac[i - 2]; } } /* get acceleration for each component */ for (i = 0; i < ncm; ++i) { pv[i + ncm * 2] = 0.0; for (j = ncf - 1; j >= 2; --j) { pv[i + ncm * 2] += ac[j] * buf[j + (i + ni * ncm) * ncf]; } pv[i + ncm * 2] *= bma2; } if (ifl == 3) { return(0); } /* check jerk polynomial values, and */ /* re-do if necessary */ bma3 = bma * bma2; jc[4] = pc[1] * 192.0; if (njk < ncf) { njk = ncf; for (i = njk; i < ncf; ++i) { jc[i] = twot * jc[i - 1] + ac[i - 1] * 6.0 - jc[i - 2]; } } /* get jerk for each component */ for (i = 0; i < ncm; ++i) { pv[i + ncm * 3] = 0.0; for (j = ncf - 1; j >= 3; --j) { pv[i + ncm * 3] += jc[j] * buf[j + (i + ni * ncm) * ncf]; } pv[i + ncm * 3] *= bma3; } return(0); }
public void swi_FK5_FK4(CPointer<double> xp, double tjd) { if (xp[0] == 0 && xp[1] == 0 && xp[2] == 0) return; swi_cartpol(xp, xp); /* according to Expl.Suppl., p. 167f. */ xp[0] -= (0.035 + 0.085 * (tjd - Sweph.B1950) / 36524.2198782) / 3600 * 15 * SwissEph.DEGTORAD; xp[3] -= (0.085 / 36524.2198782) / 3600 * 15 * SwissEph.DEGTORAD; swi_polcart(xp, xp); }
int precess_2(CPointer<double> R, double J, Int32 iflag, int direction, int prec_method) { int i; double T, z; double eps, sineps, coseps; double[] x = new double[3]; CPointer<double> p; double A, B, pA, W; double[] pAcof = null, inclcof = null, nodecof = null; if (J == Sweph.J2000) return (0); if (prec_method == SwissEph.SEMOD_PREC_LASKAR_1986) { pAcof = pAcof_laskar; nodecof = nodecof_laskar; inclcof = inclcof_laskar; } else if (prec_method == SwissEph.SEMOD_PREC_SIMON_1994) { pAcof = pAcof_simon; nodecof = nodecof_simon; inclcof = inclcof_simon; } else if (prec_method == SwissEph.SEMOD_PREC_WILLIAMS_1994) { pAcof = pAcof_williams; nodecof = nodecof_williams; inclcof = inclcof_williams; } else { /* default, to satisfy compiler */ pAcof = pAcof_laskar; nodecof = nodecof_laskar; inclcof = inclcof_laskar; } T = (J - Sweph.J2000) / 36525.0; /* Implementation by elementary rotations using Laskar's expansions. * First rotate about the x axis from the initial equator * to the ecliptic. (The input is equatorial.) */ if (direction == 1) eps = swi_epsiln(J, iflag); /* To J2000 */ else eps = swi_epsiln(Sweph.J2000, iflag); /* From J2000 */ sineps = Math.Sin(eps); coseps = Math.Cos(eps); x[0] = R[0]; z = coseps * R[1] + sineps * R[2]; x[2] = -sineps * R[1] + coseps * R[2]; x[1] = z; /* Precession in longitude */ T /= 10.0; /* thousands of years */ p = pAcof; pA = p++; for (i = 0; i < 9; i++) { pA = pA * T + p++; } pA *= SwissEph.DEGTORAD / 3600 * T; /* Node of the moving ecliptic on the J2000 ecliptic. */ p = nodecof; W = p++; for (i = 0; i < 10; i++) W = W * T + p++; /* Rotate about z axis to the node. */ if (direction == 1) z = W + pA; else z = W; B = Math.Cos(z); A = Math.Sin(z); z = B * x[0] + A * x[1]; x[1] = -A * x[0] + B * x[1]; x[0] = z; /* Rotate about new x axis by the inclination of the moving * ecliptic on the J2000 ecliptic. */ p = inclcof; z = p++; for (i = 0; i < 10; i++) z = z * T + p++; if (direction == 1) z = -z; B = Math.Cos(z); A = Math.Sin(z); z = B * x[1] + A * x[2]; x[2] = -A * x[1] + B * x[2]; x[1] = z; /* Rotate about new z axis back from the node. */ if (direction == 1) z = -W; else z = -W - pA; B = Math.Cos(z); A = Math.Sin(z); z = B * x[0] + A * x[1]; x[1] = -A * x[0] + B * x[1]; x[0] = z; /* Rotate about x axis to final equator. */ if (direction == 1) eps = swi_epsiln(Sweph.J2000, iflag); else eps = swi_epsiln(J, iflag); sineps = Math.Sin(eps); coseps = Math.Cos(eps); z = coseps * x[1] - sineps * x[2]; x[2] = sineps * x[1] + coseps * x[2]; x[1] = z; for (i = 0; i < 3; i++) R[i] = x[i]; return (0); }
/* GCRS to FK5 */ public void swi_icrs2fk5(CPointer<double> x, Int32 iflag, bool backward) { //#if 0 // double DAS2R = 1.0 / 3600.0 * DEGTORAD; // double dra0 = -0.0229 * DAS2R; // double dxi0 = 0.0091 * DAS2R; // double det0 = -0.0199 * DAS2R; //#endif double[] xx = new double[6]; double[,] rb = new double[3, 3]; int i; rb[0, 0] = +0.9999999999999928; rb[0, 1] = +0.0000001110223287; rb[0, 2] = +0.0000000441180557; rb[1, 0] = -0.0000001110223330; rb[1, 1] = +0.9999999999999891; rb[1, 2] = +0.0000000964779176; rb[2, 0] = -0.0000000441180450; rb[2, 1] = -0.0000000964779225; rb[2, 2] = +0.9999999999999943; if (backward) { for (i = 0; i <= 2; i++) { xx[i] = x[0] * rb[i, 0] + x[1] * rb[i, 1] + x[2] * rb[i, 2]; if ((iflag & SwissEph.SEFLG_SPEED) != 0) xx[i + 3] = x[3] * rb[i, 0] + x[4] * rb[i, 1] + x[5] * rb[i, 2]; } } else { for (i = 0; i <= 2; i++) { xx[i] = x[0] * rb[0, i] + x[1] * rb[1, i] + x[2] * rb[2, i]; if ((iflag & SwissEph.SEFLG_SPEED) != 0) xx[i + 3] = x[3] * rb[0, i] + x[4] * rb[1, i] + x[5] * rb[2, i]; } } for (i = 0; i <= 5; i++) x[i] = xx[i]; }
/* * Long term high precision precession, * according to Vondrak/Capitaine/Wallace, "New precession expressions, valid * for long time intervals", in A&A 534, A22(2011). */ /* precession of the ecliptic */ void pre_pecl(double tjd, CPointer<double> vec) { int i; int npol = NPOL_PECL; int nper = NPER_PECL; double t, p, q, w, a, s, c, z; t = (tjd - Sweph.J2000) / 36525.0; p = 0; q = 0; /* periodic terms */ for (i = 0; i < nper; i++) { w = D2PI * t; a = w / pqper[0, i]; s = Math.Sin(a); c = Math.Cos(a); p += c * pqper[1, i] + s * pqper[3, i]; q += c * pqper[2, i] + s * pqper[4, i]; } /* polynomial terms */ w = 1; for (i = 0; i < npol; i++) { p += pqpol[i, 0] * w; q += pqpol[i, 1] * w; w *= t; } /* both to radians */ p *= AS2R; q *= AS2R; /* ecliptic pole vector */ z = 1 - p * p - q * q; if (z < 0) z = 0; else z = Math.Sqrt(z); s = Math.Sin(EPS0); c = Math.Cos(EPS0); vec[0] = p; vec[1] = -q * c - z * s; vec[2] = -q * s + z * c; }
/* conversion from polar (l[3]) to cartesian coordinates (x[3]). * x = l is allowed. */ public void swi_polcart(CPointer<double> l, CPointer<double> x) { double[] xx = new double[3]; double cosl1; cosl1 = Math.Cos(l[1]); xx[0] = l[2] * cosl1 * Math.Cos(l[0]); xx[1] = l[2] * cosl1 * Math.Sin(l[0]); xx[2] = l[2] * Math.Sin(l[1]); x[0] = xx[0]; x[1] = xx[1]; x[2] = xx[2]; }
//#if 0 //static void swi_cross_prod(double *a, double *b, double *x) //{ // x[0] = a[1] * b[2] - a[2] * b[1]; // x[1] = a[2] * b[0] - a[0] * b[2]; // x[2] = a[0] * b[1] - a[1] * b[0]; //} //#endif /* precession matrix */ void pre_pmat(double tjd, CPointer<double> rp) { double[] peqr = new double[3], pecl = new double[3], v = new double[3], eqx = new double[3]; double w; /*equator pole */ pre_pequ(tjd, peqr); /* ecliptic pole */ pre_pecl(tjd, pecl); /* equinox */ swi_cross_prod(peqr, pecl, v); w = Math.Sqrt(v[0] * v[0] + v[1] * v[1] + v[2] * v[2]); eqx[0] = v[0] / w; eqx[1] = v[1] / w; eqx[2] = v[2] / w; swi_cross_prod(peqr, eqx, v); rp[0] = eqx[0]; rp[1] = eqx[1]; rp[2] = eqx[2]; rp[3] = v[0]; rp[4] = v[1]; rp[5] = v[2]; rp[6] = peqr[0]; rp[7] = peqr[1]; rp[8] = peqr[2]; }
/* Subroutine arguments: * * R = rectangular equatorial coordinate vector to be precessed. * The result is written back into the input vector. * J = Julian date * direction = * Precess from J to J2000: direction = 1 * Precess from J2000 to J: direction = -1 * Note that if you want to precess from J1 to J2, you would * first go from J1 to J2000, then call the program again * to go from J2000 to J2. */ public int swi_precess(CPointer<double> R, double J, Int32 iflag, int direction) { double T = (J - Sweph.J2000) / 36525.0; int prec_model = swed.astro_models[SwissEph.SE_MODEL_PREC_LONGTERM]; int prec_model_short = swed.astro_models[SwissEph.SE_MODEL_PREC_SHORTTERM]; int jplhor_model = swed.astro_models[SwissEph.SE_MODEL_JPLHOR_MODE]; if (prec_model == 0) prec_model = SwissEph.SEMOD_PREC_DEFAULT; if (prec_model_short == 0) prec_model_short = SwissEph.SEMOD_PREC_DEFAULT_SHORT; if (jplhor_model == 0) jplhor_model = SwissEph.SEMOD_JPLHOR_DEFAULT; /* JPL Horizons uses precession IAU 1976 and nutation IAU 1980 plus * some correction to nutation, arriving at extremely high precision */ /*if ((iflag & SEFLG_JPLHOR) && (jplhor_model & SEMOD_JPLHOR_DAILY_DATA)) {*/ if ((iflag & SwissEph.SEFLG_JPLHOR) != 0/*&& INCLUDE_CODE_FOR_DPSI_DEPS_IAU1980*/) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_IAU_1976); /* Use IAU 1976 formula for a few centuries. */ } else if (prec_model_short == SwissEph.SEMOD_PREC_IAU_1976 && Math.Abs(T) <= PREC_IAU_1976_CTIES) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_IAU_1976); } else if (prec_model == SwissEph.SEMOD_PREC_IAU_1976) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_IAU_1976); /* Use IAU 2000 formula for a few centuries. */ } else if (prec_model_short == SwissEph.SEMOD_PREC_IAU_2000 && Math.Abs(T) <= PREC_IAU_2000_CTIES) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_IAU_2000); } else if (prec_model == SwissEph.SEMOD_PREC_IAU_2000) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_IAU_2000); /* Use IAU 2006 formula for a few centuries. */ } else if (prec_model_short == SwissEph.SEMOD_PREC_IAU_2006 && Math.Abs(T) <= PREC_IAU_2006_CTIES) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_IAU_2006); } else if (prec_model == SwissEph.SEMOD_PREC_IAU_2006) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_IAU_2006); } else if (prec_model == SwissEph.SEMOD_PREC_BRETAGNON_2003) { return precess_1(R, J, direction, SwissEph.SEMOD_PREC_BRETAGNON_2003); } else if (prec_model == SwissEph.SEMOD_PREC_LASKAR_1986) { return precess_2(R, J, iflag, direction, SwissEph.SEMOD_PREC_LASKAR_1986); } else if (prec_model == SwissEph.SEMOD_PREC_SIMON_1994) { return precess_2(R, J, iflag, direction, SwissEph.SEMOD_PREC_SIMON_1994); } else { /* SEMOD_PREC_VONDRAK_2011 */ return precess_3(R, J, direction, SwissEph.SEMOD_PREC_VONDRAK_2011); } }
int swi_nutation_iau1980(double J, CPointer<double> nutlo) { /* arrays to hold sines and cosines of multiple angles */ double[,] ss = new double[5, 8]; double[,] cc = new double[5, 8]; double arg; double[] args = new double[5]; double f, g, T, T2; double MM, MS, FF, DD, OM; double cu, su, cv, sv, sw, s; double C, D; int i, j, k, k1, m, n; int[] ns = new int[5]; CPointer<short> p; int nut_model = swed.astro_models[SwissEph.SE_MODEL_NUT]; if (nut_model == 0) nut_model = SwissEph.SEMOD_NUT_DEFAULT; /* Julian centuries from 2000 January 1.5, * barycentric dynamical time */ T = (J - 2451545.0) / 36525.0; T2 = T * T; /* Fundamental arguments in the FK5 reference system. * The coefficients, originally given to 0.001", * are converted here to degrees. */ /* longitude of the mean ascending node of the lunar orbit * on the ecliptic, measured from the mean equinox of date */ OM = -6962890.539 * T + 450160.280 + (0.008 * T + 7.455) * T2; OM = swe_degnorm(OM / 3600) * SwissEph.DEGTORAD; /* mean longitude of the Sun minus the * mean longitude of the Sun's perigee */ MS = 129596581.224 * T + 1287099.804 - (0.012 * T + 0.577) * T2; MS = swe_degnorm(MS / 3600) * SwissEph.DEGTORAD; /* mean longitude of the Moon minus the * mean longitude of the Moon's perigee */ MM = 1717915922.633 * T + 485866.733 + (0.064 * T + 31.310) * T2; MM = swe_degnorm(MM / 3600) * SwissEph.DEGTORAD; /* mean longitude of the Moon minus the * mean longitude of the Moon's node */ FF = 1739527263.137 * T + 335778.877 + (0.011 * T - 13.257) * T2; FF = swe_degnorm(FF / 3600) * SwissEph.DEGTORAD; /* mean elongation of the Moon from the Sun. */ DD = 1602961601.328 * T + 1072261.307 + (0.019 * T - 6.891) * T2; DD = swe_degnorm(DD / 3600) * SwissEph.DEGTORAD; args[0] = MM; ns[0] = 3; args[1] = MS; ns[1] = 2; args[2] = FF; ns[2] = 4; args[3] = DD; ns[3] = 4; args[4] = OM; ns[4] = 2; /* Calculate Math.Sin( i*MM ), etc. for needed multiple angles */ for (k = 0; k <= 4; k++) { arg = args[k]; n = ns[k]; su = Math.Sin(arg); cu = Math.Cos(arg); ss[k, 0] = su; /* sin(L) */ cc[k, 0] = cu; /* cos(L) */ sv = 2.0 * su * cu; cv = cu * cu - su * su; ss[k, 1] = sv; /* sin(2L) */ cc[k, 1] = cv; for (i = 2; i < n; i++) { s = su * cv + cu * sv; cv = cu * cv - su * sv; sv = s; ss[k, i] = sv; /* sin( i+1 L ) */ cc[k, i] = cv; } } /* first terms, not in table: */ C = (-0.01742 * T - 17.1996) * ss[4, 0]; /* sin(OM) */ D = (0.00089 * T + 9.2025) * cc[4, 0]; /* cos(OM) */ for (p = nt; p != Sweph.ENDMARK; p += 9) { if (nut_model != SwissEph.SEMOD_NUT_IAU_CORR_1987 && (p[0] == 101 || p[0] == 102)) continue; /* argument of sine and cosine */ k1 = 0; cv = 0.0; sv = 0.0; for (m = 0; m < 5; m++) { j = p[m]; if (j > 100) j = 0; /* p[0] is a flag */ if (j != 0) { k = j; if (j < 0) k = -k; su = ss[m, k - 1]; /* sin(k*angle) */ if (j < 0) su = -su; cu = cc[m, k - 1]; if (k1 == 0) { /* set first angle */ sv = su; cv = cu; k1 = 1; } else { /* combine angles */ sw = su * cv + cu * sv; cv = cu * cv - su * sv; sv = sw; } } } /* longitude coefficient, in 0.0001" */ f = p[5] * 0.0001; if (p[6] != 0) f += 0.00001 * T * p[6]; /* obliquity coefficient, in 0.0001" */ g = p[7] * 0.0001; if (p[8] != 0) g += 0.00001 * T * p[8]; if (p >= 100) { /* coefficients in 0.00001" */ f *= 0.1; g *= 0.1; } /* accumulate the terms */ if (p != 102) { C += f * sv; D += g * cv; } else { /* cos for nutl and sin for nuto */ C += f * cv; D += g * sv; } /* if (i >= 105) { printf("%4.10f, %4.10f\n",f*sv,g*cv); } */ } /* printf("%4.10f, %4.10f, %4.10f, %4.10f\n",MS*RADTODEG,FF*RADTODEG,DD*RADTODEG,OM*RADTODEG); printf( "nutation: in longitude %.9f\", in obliquity %.9f\"\n", C, D ); */ /* Save answers, expressed in radians */ nutlo[0] = SwissEph.DEGTORAD * C / 3600.0; nutlo[1] = SwissEph.DEGTORAD * D / 3600.0; return (0); }
/* Precession of the equinox and ecliptic * from epoch Julian date J to or from J2000.0 * * Original program by Steve Moshier. * Changes in program structure and implementation of IAU 2003 (P03) and * Vondrak 2011 by Dieter Koch. * * SEMOD_PREC_VONDRAK_2011 1 * J. Vondrák, N. Capitaine, and P. Wallace, "New precession expressions, * valid for long time intervals", A&A 534, A22 (2011) * * SEMOD_PREC_IAU_2006 0 * N. Capitaine, P.T. Wallace, and J. Chapront, "Expressions for IAU 2000 * precession quantities", 2003, A&A 412, 567-568 (2003). * This is a "short" term model, that can be combined with other models * * SEMOD_PREC_WILLIAMS_1994 0 * James G. Williams, "Contributions to the Earth's obliquity rate, * precession, and nutation," Astron. J. 108, 711-724 (1994). * * SEMOD_PREC_SIMON_1994 0 * J. L. Simon, P. Bretagnon, J. Chapront, M. Chapront-Touze', G. Francou, * and J. Laskar, "Numerical Expressions for precession formulae and * mean elements for the Moon and the planets," Astronomy and Astrophysics * 282, 663-683 (1994). * * SEMOD_PREC_IAU_1976 0 * IAU Coefficients are from: * J. H. Lieske, T. Lederle, W. Fricke, and B. Morando, * "Expressions for the Precession Quantities Based upon the IAU * (1976) System of Astronomical Constants," Astronomy and * Astrophysics 58, 1-16 (1977). * This is a "short" term model, that can be combined with other models * * SEMOD_PREC_LASKAR_1986 0 * Newer formulas that cover a much longer time span are from: * J. Laskar, "Secular terms of classical planetary theories * using the results of general theory," Astronomy and Astrophysics * 157, 59070 (1986). * * See also: * P. Bretagnon and G. Francou, "Planetary theories in rectangular * and spherical variables. VSOP87 solutions," Astronomy and * Astrophysics 202, 309-315 (1988). * * Bretagnon and Francou's expansions for the node and inclination * of the ecliptic were derived from Laskar's data but were truncated * after the term in T**6. I have recomputed these expansions from * Laskar's data, retaining powers up to T**10 in the result. * */ int precess_1(CPointer<double> R, double J, int direction, int prec_method) { double T = 0, Z = 0, z = 0, TH = 0; int i; double[] x = new double[3]; double sinth, costh, sinZ, cosZ, sinz, cosz, A, B; if (J == Sweph.J2000) return (0); T = (J - Sweph.J2000) / 36525.0; if (prec_method == SwissEph.SEMOD_PREC_IAU_1976) { Z = ((0.017998 * T + 0.30188) * T + 2306.2181) * T * SwissEph.DEGTORAD / 3600; z = ((0.018203 * T + 1.09468) * T + 2306.2181) * T * SwissEph.DEGTORAD / 3600; TH = ((-0.041833 * T - 0.42665) * T + 2004.3109) * T * SwissEph.DEGTORAD / 3600; } else if (prec_method == SwissEph.SEMOD_PREC_IAU_2000) { /* AA 2006 B28:*/ Z = (((((-0.0000002 * T - 0.0000327) * T + 0.0179663) * T + 0.3019015) * T + 2306.0809506) * T + 2.5976176) * SwissEph.DEGTORAD / 3600; z = (((((-0.0000003 * T - 0.000047) * T + 0.0182237) * T + 1.0947790) * T + 2306.0803226) * T - 2.5976176) * SwissEph.DEGTORAD / 3600; TH = ((((-0.0000001 * T - 0.0000601) * T - 0.0418251) * T - 0.4269353) * T + 2004.1917476) * T * SwissEph.DEGTORAD / 3600; } else if (prec_method == SwissEph.SEMOD_PREC_IAU_2006) { T = (J - Sweph.J2000) / 36525.0; Z = (((((-0.0000003173 * T - 0.000005971) * T + 0.01801828) * T + 0.2988499) * T + 2306.083227) * T + 2.650545) * SwissEph.DEGTORAD / 3600; z = (((((-0.0000002904 * T - 0.000028596) * T + 0.01826837) * T + 1.0927348) * T + 2306.077181) * T - 2.650545) * SwissEph.DEGTORAD / 3600; TH = ((((-0.00000011274 * T - 0.000007089) * T - 0.04182264) * T - 0.4294934) * T + 2004.191903) * T * SwissEph.DEGTORAD / 3600; } else if (prec_method == SwissEph.SEMOD_PREC_BRETAGNON_2003) { TH = ((-0.041833 * T - 0.42665) * T + 2004.3109) * T * SwissEph.DEGTORAD / 3600; Z = ((((((-0.00000000013 * T - 0.0000003040) * T - 0.000005708) * T + 0.01801752) * T + 0.3023262) * T + 2306.080472) * T + 2.72767) * SwissEph.DEGTORAD / 3600; z = ((((((-0.00000000005 * T - 0.0000002486) * T - 0.000028276) * T + 0.01826676) * T + 1.0956768) * T + 2306.076070) * T - 2.72767) * SwissEph.DEGTORAD / 3600; TH = ((((((0.000000000009 * T + 0.00000000036) * T - 0.0000001127) * T - 0.000007291) * T - 0.04182364) * T - 0.4266980) * T + 2004.190936) * T * SwissEph.DEGTORAD / 3600; } else { return 0; } sinth = Math.Sin(TH); costh = Math.Cos(TH); sinZ = Math.Sin(Z); cosZ = Math.Cos(Z); sinz = Math.Sin(z); cosz = Math.Cos(z); A = cosZ * costh; B = sinZ * costh; if (direction < 0) { /* From J2000.0 to J */ x[0] = (A * cosz - sinZ * sinz) * R[0] - (B * cosz + cosZ * sinz) * R[1] - sinth * cosz * R[2]; x[1] = (A * sinz + sinZ * cosz) * R[0] - (B * sinz - cosZ * cosz) * R[1] - sinth * sinz * R[2]; x[2] = cosZ * sinth * R[0] - sinZ * sinth * R[1] + costh * R[2]; } else { /* From J to J2000.0 */ x[0] = (A * cosz - sinZ * sinz) * R[0] + (A * sinz + sinZ * cosz) * R[1] + cosZ * sinth * R[2]; x[1] = -(B * cosz + cosZ * sinz) * R[0] - (B * sinz - cosZ * cosz) * R[1] - sinZ * sinth * R[2]; x[2] = -sinth * cosz * R[0] - sinth * sinz * R[1] + costh * R[2]; } for (i = 0; i < 3; i++) R[i] = x[i]; return (0); }
int state(double et, Int32[] list, bool do_bary, CPointer <double> pv, CPointer <double> pvsun, CPointer <double> nut, ref string serr) { int i, j, k; Int32 nseg; Int64 flen, nb; double[] buf = js.buf; double aufac, s, t, intv; double[] ts = new double[4]; Int32 nrecl, ksize; Int32 nr; double et_mn, et_fr; Int32[] ipt = js.eh_ipt; sbyte[] ch_ttl = new sbyte[252]; if (js.jplfptr == null) { ksize = fsizer(ref serr); /* the number of single precision words in a record */ nrecl = 4; if (ksize == Sweph.NOT_AVAILABLE) { return(Sweph.NOT_AVAILABLE); } irecsz = nrecl * ksize; /* record size in bytes */ ncoeffs = ksize / 2; /* # of coefficients, doubles */ /* ttl = ephemeris title, e.g. * "JPL Planetary Ephemeris DE404/LE404 * Start Epoch: JED= 625296.5-3001 DEC 21 00:00:00 * Final Epoch: JED= 2817168.5 3001 JAN 17 00:00:00c */ //fread((void *) ch_ttl, 1, 252, js.jplfptr); ch_ttl = js.jplfptr.ReadSBytes(252); /* cnam = names of constants */ //fread((void *) js.ch_cnam, 1, 2400, js.jplfptr); js.ch_cnam = js.jplfptr.ReadChars(2400); /* ss[0] = start epoch of ephemeris * ss[1] = end epoch * ss[2] = segment size in days */ //fread((void *) &js.eh_ss[0], sizeof(double), 3, js.jplfptr); js.eh_ss = js.jplfptr.ReadDoubles(3); if (js.do_reorder) { //reorder((char *) &js.eh_ss[0], sizeof(double), 3); reorder(js.eh_ss); } /* ncon = number of constants */ //fread((void *) &js.eh_ncon, sizeof(int32), 1, js.jplfptr); js.eh_ncon = js.jplfptr.ReadInt32(); if (js.do_reorder) { //reorder((char *) &js.eh_ncon, sizeof(int32), 1); js.eh_ncon = reorder(js.eh_ncon); } /* au = astronomical unit */ //fread((void *) &js.eh_au, sizeof(double), 1, js.jplfptr); js.eh_au = js.jplfptr.ReadDouble(); if (js.do_reorder) { //reorder((char *) &js.eh_au, sizeof(double), 1); js.eh_au = reorder(js.eh_au); } /* emrat = earth moon mass ratio */ //fread((void *) &js.eh_emrat, sizeof(double), 1, js.jplfptr); js.eh_emrat = js.jplfptr.ReadDouble(); if (js.do_reorder) { //reorder((char *) &js.eh_emrat, sizeof(double), 1); js.eh_emrat = reorder(js.eh_emrat); } /* ipt[i+0]: coefficients of planet i start at buf[ipt[i+0]-1] * ipt[i+1]: number of coefficients (interpolation order - 1) * ipt[i+2]: number of intervals in segment */ //fread((void *) &ipt[0], sizeof(int32), 36, js.jplfptr); js.jplfptr.ReadInt32s(ipt, 0, 36); if (js.do_reorder) { //reorder((char *) &ipt[0], sizeof(int32), 36); reorder(ipt, 0, 36); } /* numde = number of jpl ephemeris "404" with de404 */ //fread((void *) &js.eh_denum, sizeof(int32), 1, js.jplfptr); js.eh_denum = js.jplfptr.ReadInt32(); if (js.do_reorder) { //reorder((char *) &js.eh_denum, sizeof(int32), 1); js.eh_denum = reorder(js.eh_denum); } //fread((void *) &lpt[0], sizeof(int32), 3, js.jplfptr); lpt = js.jplfptr.ReadInt32s(3); if (js.do_reorder) { //reorder((char *) &lpt[0], sizeof(int32), 3); reorder(lpt); } /* cval[]: other constants in next record */ //FSEEK(js.jplfptr, (off_t) (1L * irecsz), 0); js.jplfptr.Seek(irecsz, SeekOrigin.Begin); //fread((void *) &js.eh_cval[0], sizeof(double), 400, js.jplfptr); js.eh_cval = js.jplfptr.ReadDoubles(400); if (js.do_reorder) { //reorder((char *) &js.eh_cval[0], sizeof(double), 400); reorder(js.eh_cval); } /* new 26-aug-2008: verify correct block size */ for (i = 0; i < 3; ++i) { ipt[i + 36] = lpt[i]; } nrl = 0; /* is file length correct? */ /* file length */ //FSEEK(js.jplfptr, (off_t) 0L, SEEK_END); js.jplfptr.Seek(0, SeekOrigin.End); //flen = FTELL(js.jplfptr); flen = js.jplfptr.Position; /* # of segments in file */ nseg = (Int32)((js.eh_ss[1] - js.eh_ss[0]) / js.eh_ss[2]); /* sum of all cheby coeffs of all planets and segments */ for (i = 0, nb = 0; i < 13; i++) { k = 3; if (i == 11) { k = 2; } nb += (ipt[i * 3 + 1] * ipt[i * 3 + 2]) * k * nseg; } /* add start and end epochs of segments */ nb += 2 * nseg; /* doubles to bytes */ nb *= 8; /* add size of header and constants section */ nb += 2 * ksize * nrecl; if (flen != nb /* some of our files are one record too long */ && flen - nb != ksize * nrecl ) { //serr=C.sprintf("JPL ephemeris file is mutilated; length = %d instead of %d.", (uint)flen, (uint)nb); serr = C.sprintf("JPL ephemeris file %s is mutilated; length = %d instead of %d.", js.jplfname, flen, nb); return(Sweph.NOT_AVAILABLE); } /* check if start and end dates in segments are the same as in * file header */ //FSEEK(js.jplfptr, (off_t) (2L * irecsz), 0); js.jplfptr.Seek(2 * irecsz, SeekOrigin.Begin); //fread((void *) &ts[0], sizeof(double), 2, js.jplfptr); js.jplfptr.ReadDoubles(ts, 0, 2); if (js.do_reorder) { //reorder((char *) &ts[0], sizeof(double), 2); reorder(ts, 0, 2); } //FSEEK(js.jplfptr, (off_t)((nseg + 2 - 1) * ((off_t)irecsz)), 0); js.jplfptr.Seek((((Int64)nseg + 2 - 1) * ((Int64)irecsz)), SeekOrigin.Begin); //fread((void*)&ts[2], sizeof(double), 2, js.jplfptr); js.jplfptr.ReadDoubles(ts, 2, 2); if (js.do_reorder) { //reorder((char*)&ts[2], sizeof(double), 2); reorder(ts, 2, 2); } if (ts[0] != js.eh_ss[0] || ts[3] != js.eh_ss[1]) { serr = C.sprintf("JPL ephemeris file is corrupt; start/end date check failed. %.1f != %.1f || %.1f != %.1f", ts[0], js.eh_ss[0], ts[3], js.eh_ss[1]); return(Sweph.NOT_AVAILABLE); } } if (list == null) { return(0); } s = et - 0.5; et_mn = Math.Floor(s); et_fr = s - et_mn; /* fraction of days since previous midnight */ et_mn += 0.5; /* midnight before epoch */ /* error return for epoch out of range */ if (et < js.eh_ss[0] || et > js.eh_ss[1]) { serr = C.sprintf("jd %f outside JPL eph. range %.2f .. %.2f;", et, js.eh_ss[0], js.eh_ss[1]); return(Sweph.BEYOND_EPH_LIMITS); } /* calculate record # and relative time in interval */ nr = (Int32)((et_mn - js.eh_ss[0]) / js.eh_ss[2]) + 2; if (et_mn == js.eh_ss[1]) { --nr; /* end point of ephemeris, use last record */ } t = (et_mn - ((nr - 2) * js.eh_ss[2] + js.eh_ss[0]) + et_fr) / js.eh_ss[2]; /* read correct record if not in core */ if (nr != nrl) { nrl = nr; //if (FSEEK(js.jplfptr, (off_t)(nr * ((off_t)irecsz)), 0) != 0) { if (js.jplfptr.Seek((nr * (irecsz)), SeekOrigin.Begin) != 0) { serr = C.sprintf("Read error in JPL eph. at %f\n", et); return(Sweph.NOT_AVAILABLE); } for (k = 1; k <= ncoeffs; ++k) { //if (fread((void*)&buf[k - 1], sizeof(double), 1, js.jplfptr) != 1) { // if (serr != NULL) // serr=C.sprintf("Read error in JPL eph. at %f\n", et); // return NOT_AVAILABLE; //} try { buf[k - 1] = js.jplfptr.ReadDouble(); } catch { serr = C.sprintf("Read error in JPL eph. at %f\n", et); return(Sweph.NOT_AVAILABLE); } if (js.do_reorder) { //reorder((char*)&buf[k - 1], sizeof(double), 1); buf[k - 1] = reorder(buf[k - 1]); } } } if (js.do_km) { intv = js.eh_ss[2] * 86400.0; aufac = 1.0; } else { intv = js.eh_ss[2]; aufac = 1.0 / js.eh_au; } /* interpolate ssbary sun */ //interp(buf[(int)ipt[30] - 1], t, intv, ipt[31], 3L, ipt[32], 2, pvsun); interp(buf.GetPointer(ipt[30] - 1), t, intv, ipt[31], 3, ipt[32], 2, pvsun); for (i = 0; i < 6; ++i) { pvsun[i] *= aufac; } /* check and interpolate whichever bodies are requested */ for (i = 0; i < 10; ++i) { if (list[i] > 0) { interp(buf.GetPointer(ipt[i * 3] - 1), t, intv, ipt[i * 3 + 1], 3, ipt[i * 3 + 2], list[i], pv + (i * 6)); for (j = 0; j < 6; ++j) { if (i < 9 && !do_bary) { pv[j + i * 6] = pv[j + i * 6] * aufac - pvsun[j]; } else { pv[j + i * 6] *= aufac; } } } } /* do nutations if requested (and if on file) */ if (list[10] > 0 && ipt[34] > 0) { interp(buf.GetPointer((int)ipt[33] - 1), t, intv, ipt[34], 2, ipt[35], list[10], nut); } /* get librations if requested (and if on file) */ if (list[11] > 0 && ipt[37] > 0) { interp(buf.GetPointer((int)ipt[36] - 1), t, intv, ipt[37], 3, ipt[38], list[1], pv + 60); } return(SwissEph.OK); }
int precess_3(CPointer<double> R, double J, int direction, int prec_meth) { double T; double[] x = new double[3], pmat = new double[9]; int i, j; if (J == Sweph.J2000) return (0); /* Each precession angle is specified by a polynomial in * T = Julian centuries from J2000.0. See AA page B18. */ T = (J - Sweph.J2000) / 36525.0; pre_pmat(J, pmat); if (direction == -1) { for (i = 0, j = 0; i <= 2; i++, j = i * 3) { x[i] = R[0] * pmat[j + 0] + R[1] * pmat[j + 1] + R[2] * pmat[j + 2]; } } else { for (i = 0, j = 0; i <= 2; i++, j = i * 3) { x[i] = R[0] * pmat[i + 0] + R[1] * pmat[i + 3] + R[2] * pmat[i + 6]; } } for (i = 0; i < 3; i++) R[i] = x[i]; return (0); }
/* * conversion between ecliptical and equatorial polar coordinates. * for users of SWISSEPH, not used by our routines. * for ecl. to equ. eps must be negative. * for equ. to ecl. eps must be positive. * xpo, xpn are arrays of 3 doubles containing position. * attention: input must be in degrees! */ public void swe_cotrans(CPointer<double> xpo, CPointer<double> xpn, double eps) { int i; double[] x = new double[6]; double e = eps * SwissEph.DEGTORAD; for (i = 0; i <= 1; i++) x[i] = xpo[i]; x[0] *= SwissEph.DEGTORAD; x[1] *= SwissEph.DEGTORAD; x[2] = 1; for (i = 3; i <= 5; i++) x[i] = 0; swi_polcart(x, x); swi_coortrf(x, x, e); swi_cartpol(x, x); xpn[0] = x[0] * SwissEph.RADTODEG; xpn[1] = x[1] * SwissEph.RADTODEG; xpn[2] = xpo[2]; }
/* precession of the equator */ void pre_pequ(double tjd, CPointer<double> veq) { int i; int npol = NPOL_PEQU; int nper = NPER_PEQU; double t, x, y, w, a, s, c; t = (tjd - Sweph.J2000) / 36525.0; x = 0; y = 0; for (i = 0; i < nper; i++) { w = D2PI * t; a = w / xyper[0, i]; s = Math.Sin(a); c = Math.Cos(a); x += c * xyper[1, i] + s * xyper[3, i]; y += c * xyper[2, i] + s * xyper[4, i]; } /* polynomial terms */ w = 1; for (i = 0; i < npol; i++) { x += xypol[i, 0] * w; y += xypol[i, 1] * w; w *= t; } x *= AS2R; y *= AS2R; /* equator pole vector */ veq[0] = x; veq[1] = y; w = x * x + y * y; if (w < 1) veq[2] = Math.Sqrt(1 - w); else veq[2] = 0; }
public CStruct(CPointer Pointer) { }
void swi_approx_jplhor(CPointer<double> x, double tjd, Int32 iflag, bool backward) { double t0, t1; double t = (tjd - DCOR_RA_JPL_TJD0) / 365.25; double dofs = OFFSET_JPLHORIZONS; int jplhor_model = swed.astro_models[SwissEph.SE_MODEL_JPLHOR_MODE]; int jplhora_model = swed.astro_models[SwissEph.SE_MODEL_JPLHORA_MODE]; if (jplhor_model == 0) jplhor_model = SwissEph.SEMOD_JPLHOR_DEFAULT; if (jplhora_model == 0) jplhora_model = SwissEph.SEMOD_JPLHORA_DEFAULT; if (0 == (iflag & SwissEph.SEFLG_JPLHOR_APPROX)) return; if (jplhora_model != SwissEph.SEMOD_JPLHORA_1) return; if (t < 0) { t = 0; dofs = dcor_ra_jpl[0]; } else if (t >= NDCOR_RA_JPL - 1) { t = NDCOR_RA_JPL; dofs = dcor_ra_jpl[NDCOR_RA_JPL - 1]; } else { t0 = (int)t; t1 = t0 + 1; dofs = dcor_ra_jpl[(int)t0]; dofs = (t - t0) * (dcor_ra_jpl[(int)t0] - dcor_ra_jpl[(int)t1]) + dcor_ra_jpl[(int)t0]; } dofs /= (1000.0 * 3600.0); swi_cartpol(x, x); if (backward) x[0] -= dofs * SwissEph.DEGTORAD; else x[0] += dofs * SwissEph.DEGTORAD; swi_polcart(x, x); }
public double swi_dot_prod_unit(CPointer<double> x, CPointer<double> y) { double dop = x[0] * y[0] + x[1] * y[1] + x[2] * y[2]; double e1 = Math.Sqrt(x[0] * x[0] + x[1] * x[1] + x[2] * x[2]); double e2 = Math.Sqrt(y[0] * y[0] + y[1] * y[1] + y[2] * y[2]); dop /= e1; dop /= e2; if (dop > 1) dop = 1; if (dop < -1) dop = -1; return dop; }
/* Nutation IAU 2000A model * (MHB2000 luni-solar and planetary nutation, without free core nutation) * * Function returns nutation in longitude and obliquity in radians with * respect to the equinox of date. For the obliquity of the ecliptic * the calculation of Lieske & al. (1977) must be used. * * The precision in recent years is about 0.001 arc seconds. * * The calculation includes luni-solar and planetary nutation. * Free core nutation, which cannot be predicted, is omitted, * the error being of the order of a few 0.0001 arc seconds. * * References: * * Capitaine, N., Wallace, P.T., Chapront, J., A & A 432, 366 (2005). * * Chapront, J., Chapront-Touze, M. & Francou, G., A & A 387, 700 (2002). * * Lieske, J.H., Lederle, T., Fricke, W. & Morando, B., "Expressions * for the precession quantities based upon the IAU (1976) System of * Astronomical Constants", A & A 58, 1-16 (1977). * * Mathews, P.M., Herring, T.A., Buffet, B.A., "Modeling of nutation * and precession New nutation series for nonrigid Earth and * insights into the Earth's interior", J.Geophys.Res., 107, B4, * 2002. * * Simon, J.-L., Bretagnon, P., Chapront, J., Chapront-Touze, M., * Francou, G., Laskar, J., A & A 282, 663-683 (1994). * * Souchay, J., Loysel, B., Kinoshita, H., Folgueira, M., A & A Supp. * Ser. 135, 111 (1999). * * Wallace, P.T., "Software for Implementing the IAU 2000 * Resolutions", in IERS Workshop 5.1 (2002). * * Nutation IAU 2000A series in: * Kaplan, G.H., United States Naval Observatory Circular No. 179 (Oct. 2005) * aa.usno.navy.mil/publications/docs/Circular_179.html * * MHB2000 code at * - ftp://maia.usno.navy.mil/conv2000/chapter5/IAU2000A. * - http://www.iau-sofa.rl.ac.uk/2005_0901/Downloads.html */ //#include "swenut2000a.h" int swi_nutation_iau2000ab(double J, CPointer<double> nutlo) { int i, j, k, inls; double M, SM, F, D, OM; double AL, ALSU, AF, AD, AOM, APA; double ALME, ALVE, ALEA, ALMA, ALJU, ALSA, ALUR, ALNE; double darg, sinarg, cosarg; double dpsi = 0, deps = 0; double T = (J - Sweph.J2000) / 36525.0; int nut_model = swed.astro_models[SwissEph.SE_MODEL_NUT]; if (nut_model == 0) nut_model = SwissEph.SEMOD_NUT_DEFAULT; /* luni-solar nutation */ /* Fundamental arguments, Simon & al. (1994) */ /* Mean anomaly of the Moon. */ M = swe_degnorm((485868.249036 + T * (1717915923.2178 + T * (31.8792 + T * (0.051635 + T * (-0.00024470))))) / 3600.0) * SwissEph.DEGTORAD; /* Mean anomaly of the Sun */ SM = swe_degnorm((1287104.79305 + T * (129596581.0481 + T * (-0.5532 + T * (0.000136 + T * (-0.00001149))))) / 3600.0) * SwissEph.DEGTORAD; /* Mean argument of the latitude of the Moon. */ F = swe_degnorm((335779.526232 + T * (1739527262.8478 + T * (-12.7512 + T * (-0.001037 + T * (0.00000417))))) / 3600.0) * SwissEph.DEGTORAD; /* Mean elongation of the Moon from the Sun. */ D = swe_degnorm((1072260.70369 + T * (1602961601.2090 + T * (-6.3706 + T * (0.006593 + T * (-0.00003169))))) / 3600.0) * SwissEph.DEGTORAD; /* Mean longitude of the ascending node of the Moon. */ OM = swe_degnorm((450160.398036 + T * (-6962890.5431 + T * (7.4722 + T * (0.007702 + T * (-0.00005939))))) / 3600.0) * SwissEph.DEGTORAD; /* luni-solar nutation series, in reverse order, starting with small terms */ if (nut_model == SwissEph.SEMOD_NUT_IAU_2000B) inls = SweNut200a.NLS_2000B; else inls = SweNut200a.NLS; for (i = inls - 1; i >= 0; i--) { j = i * 5; darg = swe_radnorm((double)nls[j + 0] * M + (double)nls[j + 1] * SM + (double)nls[j + 2] * F + (double)nls[j + 3] * D + (double)nls[j + 4] * OM); sinarg = Math.Sin(darg); cosarg = Math.Cos(darg); k = i * 6; dpsi += (cls[k + 0] + cls[k + 1] * T) * sinarg + cls[k + 2] * cosarg; deps += (cls[k + 3] + cls[k + 4] * T) * cosarg + cls[k + 5] * sinarg; } nutlo[0] = dpsi * SweNut200a.O1MAS2DEG; nutlo[1] = deps * SweNut200a.O1MAS2DEG; if (nut_model == SwissEph.SEMOD_NUT_IAU_2000A) { /* planetary nutation * note: The MHB2000 code computes the luni-solar and planetary nutation * in different routines, using slightly different Delaunay * arguments in the two cases. This behaviour is faithfully * reproduced here. Use of the Simon et al. expressions for both * cases leads to negligible changes, well below 0.1 microarcsecond.*/ /* Mean anomaly of the Moon.*/ AL = swe_radnorm(2.35555598 + 8328.6914269554 * T); /* Mean anomaly of the Sun.*/ ALSU = swe_radnorm(6.24006013 + 628.301955 * T); /* Mean argument of the latitude of the Moon. */ AF = swe_radnorm(1.627905234 + 8433.466158131 * T); /* Mean elongation of the Moon from the Sun. */ AD = swe_radnorm(5.198466741 + 7771.3771468121 * T); /* Mean longitude of the ascending node of the Moon. */ AOM = swe_radnorm(2.18243920 - 33.757045 * T); /* Planetary longitudes, Mercury through Neptune (Souchay et al. 1999). */ ALME = swe_radnorm(4.402608842 + 2608.7903141574 * T); ALVE = swe_radnorm(3.176146697 + 1021.3285546211 * T); ALEA = swe_radnorm(1.753470314 + 628.3075849991 * T); ALMA = swe_radnorm(6.203480913 + 334.0612426700 * T); ALJU = swe_radnorm(0.599546497 + 52.9690962641 * T); ALSA = swe_radnorm(0.874016757 + 21.3299104960 * T); ALUR = swe_radnorm(5.481293871 + 7.4781598567 * T); ALNE = swe_radnorm(5.321159000 + 3.8127774000 * T); /* General accumulated precession in longitude. */ APA = (0.02438175 + 0.00000538691 * T) * T; /* planetary nutation series (in reverse order).*/ dpsi = 0; deps = 0; for (i = SweNut200a.NPL - 1; i >= 0; i--) { j = i * 14; darg = swe_radnorm((double)npl[j + 0] * AL + (double)npl[j + 1] * ALSU + (double)npl[j + 2] * AF + (double)npl[j + 3] * AD + (double)npl[j + 4] * AOM + (double)npl[j + 5] * ALME + (double)npl[j + 6] * ALVE + (double)npl[j + 7] * ALEA + (double)npl[j + 8] * ALMA + (double)npl[j + 9] * ALJU + (double)npl[j + 10] * ALSA + (double)npl[j + 11] * ALUR + (double)npl[j + 12] * ALNE + (double)npl[j + 13] * APA); k = i * 4; sinarg = Math.Sin(darg); cosarg = Math.Cos(darg); dpsi += (double)icpl[k + 0] * sinarg + (double)icpl[k + 1] * cosarg; deps += (double)icpl[k + 2] * sinarg + (double)icpl[k + 3] * cosarg; } nutlo[0] += dpsi * SweNut200a.O1MAS2DEG; nutlo[1] += deps * SweNut200a.O1MAS2DEG; //#if 1 /* changes required by adoption of P03 precession * according to Capitaine et al. A & A 412, 366 (2005) = IAU 2006 */ dpsi = -8.1 * Math.Sin(OM) - 0.6 * Math.Sin(2 * F - 2 * D + 2 * OM); dpsi += T * (47.8 * Math.Sin(OM) + 3.7 * Math.Sin(2 * F - 2 * D + 2 * OM) + 0.6 * Math.Sin(2 * F + 2 * OM) - 0.6 * Math.Sin(2 * OM)); deps = T * (-25.6 * Math.Cos(OM) - 1.6 * Math.Cos(2 * F - 2 * D + 2 * OM)); nutlo[0] += dpsi / (3600.0 * 1000000.0); nutlo[1] += deps / (3600.0 * 1000000.0); //#endif } nutlo[0] *= SwissEph.DEGTORAD; nutlo[1] *= SwissEph.DEGTORAD; return 0; }
public const double SE_LAPSE_RATE = 0.0065; /* deg K / m, for refraction */ public double square_sum(CPointer <double> x) { return(x[0] * x[0] + x[1] * x[1] + x[2] * x[2]); }
/* * conversion between ecliptical and equatorial polar coordinates * with speed. * for users of SWISSEPH, not used by our routines. * for ecl. to equ. eps must be negative. * for equ. to ecl. eps must be positive. * xpo, xpn are arrays of 6 doubles containing position and speed. * attention: input must be in degrees! */ public void swe_cotrans_sp(CPointer<double> xpo, CPointer<double> xpn, double eps) { int i; double[] x = new double[6]; double e = eps * SwissEph.DEGTORAD; for (i = 0; i <= 5; i++) x[i] = xpo[i]; x[0] *= SwissEph.DEGTORAD; x[1] *= SwissEph.DEGTORAD; x[2] = 1; /* avoids problems with polcart(), if x[2] = 0 */ x[3] *= SwissEph.DEGTORAD; x[4] *= SwissEph.DEGTORAD; swi_polcart_sp(x, x); swi_coortrf(x, x, e); swi_coortrf(x.GetPointer(3), x.GetPointer(3), e); swi_cartpol_sp(x, xpn); xpn[0] *= SwissEph.RADTODEG; xpn[1] *= SwissEph.RADTODEG; xpn[2] = xpo[2]; xpn[3] *= SwissEph.RADTODEG; xpn[4] *= SwissEph.RADTODEG; xpn[5] = xpo[5]; }
/* * conversion between ecliptical and equatorial cartesian coordinates * sineps sin(eps) * coseps cos(eps) * for ecl. to equ. sineps must be -sin(eps) */ public void swi_coortrf2(CPointer<double> xpo, CPointer<double> xpn, double sineps, double coseps) { double[] x = new double[3]; x[0] = xpo[0]; x[1] = xpo[1] * coseps + xpo[2] * sineps; x[2] = -xpo[1] * sineps + xpo[2] * coseps; xpn[0] = x[0]; xpn[1] = x[1]; xpn[2] = x[2]; }
private void Alloc() { Pointer = new CPointer(SizeOf); }
public void swi_cross_prod(CPointer<double> a, CPointer<double> b, CPointer<double> x) { x[0] = a[1] * b[2] - a[2] * b[1]; x[1] = a[2] * b[0] - a[0] * b[2]; x[2] = a[0] * b[1] - a[1] * b[0]; }