GlobalMappingFunctionModel.java

  1. /* Copyright 2002-2019 CS Systèmes d'Information
  2.  * Licensed to CS Systèmes d'Information (CS) under one or more
  3.  * contributor license agreements.  See the NOTICE file distributed with
  4.  * this work for additional information regarding copyright ownership.
  5.  * CS licenses this file to You under the Apache License, Version 2.0
  6.  * (the "License"); you may not use this file except in compliance with
  7.  * the License.  You may obtain a copy of the License at
  8.  *
  9.  *   http://www.apache.org/licenses/LICENSE-2.0
  10.  *
  11.  * Unless required by applicable law or agreed to in writing, software
  12.  * distributed under the License is distributed on an "AS IS" BASIS,
  13.  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  14.  * See the License for the specific language governing permissions and
  15.  * limitations under the License.
  16.  */
  17. package org.orekit.models.earth;

  18. import java.util.Collections;
  19. import java.util.List;

  20. import org.hipparchus.Field;
  21. import org.hipparchus.RealFieldElement;
  22. import org.hipparchus.util.CombinatoricsUtils;
  23. import org.hipparchus.util.FastMath;
  24. import org.hipparchus.util.MathArrays;
  25. import org.orekit.time.AbsoluteDate;
  26. import org.orekit.time.DateTimeComponents;
  27. import org.orekit.time.FieldAbsoluteDate;
  28. import org.orekit.time.TimeScalesFactory;
  29. import org.orekit.utils.ParameterDriver;

  30. /** The Global Mapping Function  model for radio techniques.
  31.  *  This model is an empirical mapping function. It only needs the
  32.  *  values of the station latitude, longitude, height and the
  33.  *  date for the computations.
  34.  *  <p>
  35.  *  The Global Mapping Function is based on spherical harmonics up
  36.  *  to degree and order of 9. It was developed to be consistent
  37.  *  with the {@link ViennaOneModel Vienna1} mapping function model.
  38.  *  </p>
  39.  *
  40.  *  @see Boehm, J., A.E. Niell, P. Tregoning, H. Schuh (2006),
  41.  *       Global Mapping Functions (GMF): A new empirical mapping function based
  42.  *       on numerical weather model data, Geoph. Res. Letters, Vol. 33, L07304,
  43.  *       doi:10.1029/2005GL025545.
  44.  *
  45.  *  @see <p>Petit, G. and Luzum, B. (eds.), IERS Conventions (2010),
  46.  *       IERS Technical Note No. 36, BKG (2010)</p>
  47.  *
  48.  *  @author Bryan Cazabonne
  49.  *
  50.  */
  51. public class GlobalMappingFunctionModel implements MappingFunction {

  52.     /** Serializable UID. */
  53.     private static final long serialVersionUID = -9007141744989481150L;

  54.     /** Geodetic site latitude, radians.*/
  55.     private final double latitude;

  56.     /** Geodetic site longitude, radians.*/
  57.     private final double longitude;

  58.     /** Build a new instance.
  59.      * @param latitude geodetic latitude of the station, in radians
  60.      * @param longitude geodetic latitude of the station, in radians
  61.      */
  62.     public GlobalMappingFunctionModel(final double latitude, final double longitude) {
  63.         this.latitude  = latitude;
  64.         this.longitude = longitude;
  65.     }

  66.     /** {@inheritDoc} */
  67.     @Override
  68.     public double[] mappingFactors(final double elevation, final double height,
  69.                                    final double[] parameters, final AbsoluteDate date) {
  70.         // Day of year computation
  71.         final DateTimeComponents dtc = date.getComponents(TimeScalesFactory.getUTC());
  72.         final int dofyear = dtc.getDate().getDayOfYear();

  73.         // bh and ch constants (Boehm, J et al, 2006) | HYDROSTATIC PART
  74.         final double bh  = 0.0029;
  75.         final double c0h = 0.062;
  76.         final double c10h;
  77.         final double c11h;
  78.         final double psi;

  79.         if (FastMath.sin(latitude) > 0) {
  80.             // northern hemisphere case
  81.             c10h = 0.001;
  82.             c11h = 0.005;
  83.             psi  = 0.0;
  84.         } else {
  85.             // southern hemisphere case
  86.             c10h = 0.002;
  87.             c11h = 0.007;
  88.             psi  = FastMath.PI;
  89.         }

  90.         double t0 = 28;
  91.         if (latitude < 0) {
  92.             // southern hemisphere: t0 = 28 + an integer half of year
  93.             t0 += 183;
  94.         }
  95.         final double coef = ((dofyear + 1 - t0) / 365.25) * 2 * FastMath.PI + psi;
  96.         final double ch = c0h + ((FastMath.cos(coef) + 1) * (c11h / 2.0) + c10h) * (1.0 - FastMath.cos(latitude));

  97.         // bw and cw constants (Boehm, J et al, 2006) | WET PART
  98.         final double bw = 0.00146;
  99.         final double cw = 0.04391;

  100.         // Compute coefficients ah and aw with spherical harmonics Eq. 3 (Ref 1)

  101.         // Compute Legendre Polynomials Pnm(sin(phi))
  102.         final int degree = 9;
  103.         final int order  = 9;
  104.         final LegendrePolynomials p = new LegendrePolynomials(degree, order);

  105.         double a0Hydro   = 0.;
  106.         double amplHydro = 0.;
  107.         double a0Wet   = 0.;
  108.         double amplWet = 0.;
  109.         final ABCoefficients abCoef = new ABCoefficients();
  110.         int j = 0;
  111.         for (int n = 0; n <= 9; n++) {
  112.             for (int m = 0; m <= n; m++) {
  113.                 a0Hydro   = a0Hydro + (abCoef.getAHMean(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  114.                                 abCoef.getBHMean(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5;

  115.                 a0Wet     = a0Wet + (abCoef.getAWMean(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  116.                                 abCoef.getBWMean(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5;

  117.                 amplHydro = amplHydro + (abCoef.getAHAmplitude(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  118.                                 abCoef.getBHAmplitude(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5;

  119.                 amplWet   = amplWet + (abCoef.getAWAmplitude(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  120.                                 abCoef.getBWAmplitude(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5;

  121.                 j = j + 1;
  122.             }
  123.         }

  124.         // Eq. 2 (Ref 1)
  125.         final double ah = a0Hydro + amplHydro * FastMath.cos(coef - psi);
  126.         final double aw = a0Wet + amplWet * FastMath.cos(coef - psi);

  127.         final double[] function = new double[2];
  128.         function[0] = computeFunction(ah, bh, ch, elevation);
  129.         function[1] = computeFunction(aw, bw, cw, elevation);

  130.         // Apply height correction
  131.         final double correction = computeHeightCorrection(elevation, height);
  132.         function[0] = function[0] + correction;

  133.         return function;
  134.     }

  135.     /** {@inheritDoc} */
  136.     @Override
  137.     public <T extends RealFieldElement<T>> T[] mappingFactors(final T elevation, final T height,
  138.                                                               final T[] parameters, final FieldAbsoluteDate<T> date) {
  139.         // Day of year computation
  140.         final DateTimeComponents dtc = date.getComponents(TimeScalesFactory.getUTC());
  141.         final int dofyear = dtc.getDate().getDayOfYear();

  142.         final Field<T> field = date.getField();
  143.         final T zero = field.getZero();

  144.         // bh and ch constants (Boehm, J et al, 2006) | HYDROSTATIC PART
  145.         final T bh  = zero.add(0.0029);
  146.         final T c0h = zero.add(0.062);
  147.         final T c10h;
  148.         final T c11h;
  149.         final T psi;

  150.         // sin(latitude) > 0 -> northern hemisphere
  151.         if (FastMath.sin(latitude) > 0) {
  152.             c10h = zero.add(0.001);
  153.             c11h = zero.add(0.005);
  154.             psi  = zero;
  155.         } else {
  156.             c10h = zero.add(0.002);
  157.             c11h = zero.add(0.007);
  158.             psi  = zero.add(FastMath.PI);
  159.         }

  160.         double t0 = 28;
  161.         if (latitude < 0) {
  162.             // southern hemisphere: t0 = 28 + an integer half of year
  163.             t0 += 183;
  164.         }
  165.         final T coef = psi.add(((dofyear + 1 - t0) / 365.25) * 2 * FastMath.PI);
  166.         final T ch = c11h.divide(2.0).multiply(FastMath.cos(coef).add(1.0)).add(c10h).multiply(1 - FastMath.cos(latitude)).add(c0h);

  167.         // bw and cw constants (Boehm, J et al, 2006) | WET PART
  168.         final T bw = zero.add(0.00146);
  169.         final T cw = zero.add(0.04391);

  170.         // Compute coefficients ah and aw with spherical harmonics Eq. 3 (Ref 1)

  171.         // Compute Legendre Polynomials Pnm(sin(phi))
  172.         final int degree = 9;
  173.         final int order  = 9;
  174.         final LegendrePolynomials p = new LegendrePolynomials(degree, order);

  175.         T a0Hydro   = zero;
  176.         T amplHydro = zero;
  177.         T a0Wet     = zero;
  178.         T amplWet   = zero;
  179.         final ABCoefficients abCoef = new ABCoefficients();
  180.         int j = 0;
  181.         for (int n = 0; n <= 9; n++) {
  182.             for (int m = 0; m <= n; m++) {
  183.                 a0Hydro   = a0Hydro.add((abCoef.getAHMean(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  184.                                 abCoef.getBHMean(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5);

  185.                 a0Wet     = a0Wet.add((abCoef.getAWMean(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  186.                                 abCoef.getBWMean(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5);

  187.                 amplHydro = amplHydro.add((abCoef.getAHAmplitude(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  188.                                 abCoef.getBHAmplitude(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5);

  189.                 amplWet   = amplWet.add((abCoef.getAWAmplitude(j) * p.getPnm(n, m) * FastMath.cos(m * longitude) +
  190.                                 abCoef.getBWAmplitude(j) * p.getPnm(n, m) * FastMath.sin(m * longitude)) * 1e-5);

  191.                 j = j + 1;
  192.             }
  193.         }

  194.         // Eq. 2 (Ref 1)
  195.         final T ah = a0Hydro.add(amplHydro.multiply(FastMath.cos(coef.subtract(psi))));
  196.         final T aw = a0Wet.add(amplWet.multiply(FastMath.cos(coef.subtract(psi))));

  197.         final T[] function = MathArrays.buildArray(field, 2);
  198.         function[0] = computeFunction(ah, bh, ch, elevation);
  199.         function[1] = computeFunction(aw, bw, cw, elevation);

  200.         // Apply height correction
  201.         final T correction = computeHeightCorrection(elevation, height, field);
  202.         function[0] = function[0].add(correction);

  203.         return function;
  204.     }

  205.     /** {@inheritDoc} */
  206.     @Override
  207.     public List<ParameterDriver> getParametersDrivers() {
  208.         return Collections.emptyList();
  209.     }

  210.     /** Compute the mapping function related to the coefficient values and the elevation.
  211.      * @param a a coefficient
  212.      * @param b b coefficient
  213.      * @param c c coefficient
  214.      * @param elevation the elevation of the satellite, in radians.
  215.      * @return the value of the function at a given elevation
  216.      */
  217.     private double computeFunction(final double a, final double b, final double c, final double elevation) {
  218.         final double sinE = FastMath.sin(elevation);
  219.         // Numerator
  220.         final double numMP = 1 + a / (1 + b / (1 + c));
  221.         // Denominator
  222.         final double denMP = sinE + a / (sinE + b / (sinE + c));

  223.         final double fElevation = numMP / denMP;

  224.         return fElevation;
  225.     }

  226.     /** Compute the mapping function related to the coefficient values and the elevation.
  227.      * @param <T> type of the elements
  228.      * @param a a coefficient
  229.      * @param b b coefficient
  230.      * @param c c coefficient
  231.      * @param elevation the elevation of the satellite, in radians.
  232.      * @return the value of the function at a given elevation
  233.      */
  234.     private <T extends RealFieldElement<T>> T computeFunction(final T a, final T b, final T c, final T elevation) {
  235.         final T sinE = FastMath.sin(elevation);
  236.         // Numerator
  237.         final T numMP = a.divide(b.divide(c.add(1.0)).add(1.0)).add(1.0);
  238.         // Denominator
  239.         final T denMP = a.divide(b.divide(c.add(sinE)).add(sinE)).add(sinE);

  240.         final T fElevation = numMP.divide(denMP);

  241.         return fElevation;
  242.     }

  243.     /** This method computes the height correction for the hydrostatic
  244.      *  component of the mapping function.
  245.      *  The formulas are given by Neill's paper, 1996:
  246.      *<p>
  247.      *      Niell A. E. (1996)
  248.      *      "Global mapping functions for the atmosphere delay of radio wavelengths,”
  249.      *      J. Geophys. Res., 101(B2), pp.  3227–3246, doi:  10.1029/95JB03048.
  250.      *</p>
  251.      * @param elevation the elevation of the satellite, in radians.
  252.      * @param height the height of the station in m above sea level.
  253.      * @return the height correction, in m
  254.      */
  255.     private double computeHeightCorrection(final double elevation, final double height) {
  256.         final double fixedHeight = FastMath.max(0.0, height);
  257.         final double sinE = FastMath.sin(elevation);
  258.         // Ref: Eq. 4
  259.         final double function = computeFunction(2.53e-5, 5.49e-3, 1.14e-3, elevation);
  260.         // Ref: Eq. 6
  261.         final double dmdh = (1 / sinE) - function;
  262.         // Ref: Eq. 7
  263.         final double correction = dmdh * (fixedHeight / 1000.0);
  264.         return correction;
  265.     }

  266.     /** This method computes the height correction for the hydrostatic
  267.      *  component of the mapping function.
  268.      *  The formulas are given by Neill's paper, 1996:
  269.      *<p>
  270.      *      Niell A. E. (1996)
  271.      *      "Global mapping functions for the atmosphere delay of radio wavelengths,”
  272.      *      J. Geophys. Res., 101(B2), pp.  3227–3246, doi:  10.1029/95JB03048.
  273.      *</p>
  274.      * @param <T> type of the elements
  275.      * @param elevation the elevation of the satellite, in radians.
  276.      * @param height the height of the station in m above sea level.
  277.      * @param field field to which the elements belong
  278.      * @return the height correction, in m
  279.      */
  280.     private <T extends RealFieldElement<T>> T computeHeightCorrection(final T elevation, final T height, final Field<T> field) {
  281.         final T zero = field.getZero();
  282.         final T fixedHeight = FastMath.max(zero, height);
  283.         final T sinE = FastMath.sin(elevation);
  284.         // Ref: Eq. 4
  285.         final T function = computeFunction(zero.add(2.53e-5), zero.add(5.49e-3), zero.add(1.14e-3), elevation);
  286.         // Ref: Eq. 6
  287.         final T dmdh = sinE.reciprocal().subtract(function);
  288.         // Ref: Eq. 7
  289.         final T correction = dmdh.multiply(fixedHeight.divide(1000.0));
  290.         return correction;
  291.     }

  292.     /** Computes the P<sub>nm</sub>(sin(&#934)) coefficients of Eq. 3 (Boehm et al, 2006).
  293.      *  The computation of the Legendre polynomials is performed following:
  294.      *  Heiskanen and Moritz, Physical Geodesy, 1967, eq. 1-62
  295.      *  <p>
  296.      *    This computation is the one used by the IERS 2010 Conventions.
  297.      *    Petit, G. and Luzum, B. (eds.), IERS Conventions (2010),
  298.      *    IERS Technical Note No. 36, BKG (2010)
  299.      *  </p>
  300.      */
  301.     private class LegendrePolynomials {

  302.         /** Array for the Legendre polynomials. */
  303.         private double[][] pCoef;

  304.         /** Create Legendre polynomials for the given degree and order.
  305.          * @param degree degree of the spherical harmonics
  306.          * @param order order of the spherical harmonics
  307.          */
  308.         LegendrePolynomials(final int degree, final int order) {

  309.             this.pCoef = new double[degree + 1][order + 1];

  310.             final double t  = FastMath.sin(latitude);
  311.             final double t2 = t * t;

  312.             for (int n = 0; n <= degree; n++) {

  313.                 // m shall be <= n (Heiskanen and Moritz, 1967, pp 21)
  314.                 for (int m = 0; m <= FastMath.min(n, order); m++) {

  315.                     // r = int((n - m) / 2)
  316.                     final int r = (int) (n - m) / 2;
  317.                     double sum = 0.;
  318.                     for (int k = 0; k <= r; k++) {
  319.                         final double term = FastMath.pow(-1.0, k) * CombinatoricsUtils.factorialDouble(2 * n - 2 * k) /
  320.                                         (CombinatoricsUtils.factorialDouble(k) * CombinatoricsUtils.factorialDouble(n - k) *
  321.                                          CombinatoricsUtils.factorialDouble(n - m - 2 * k)) *
  322.                                          FastMath.pow(t, n - m - 2 * k);
  323.                         sum = sum + term;
  324.                     }

  325.                     pCoef[n][m] = FastMath.pow(2, -n) * FastMath.pow(1.0 - t2, 0.5 * m) * sum;

  326.                 }

  327.             }

  328.         }

  329.         /** Return the coefficient P<sub>nm</sub>.
  330.          * @param n index
  331.          * @param m index
  332.          * @return The coefficient P<sub>nm</sub>
  333.          */
  334.         public double getPnm(final int n, final int m) {
  335.             return pCoef[n][m];
  336.         }

  337.     }

  338.     private static class ABCoefficients {

  339.         /** Mean hydrostatic coefficients a.*/
  340.         private static final double[] AH_MEAN = {
  341.             1.2517e02,
  342.             8.503e-01,
  343.             6.936e-02,
  344.             -6.760e+00,
  345.             1.771e-01,
  346.             1.130e-02,
  347.             5.963e-01,
  348.             1.808e-02,
  349.             2.801e-03,
  350.             -1.414e-03,
  351.             -1.212e+00,
  352.             9.300e-02,
  353.             3.683e-03,
  354.             1.095e-03,
  355.             4.671e-05,
  356.             3.959e-01,
  357.             -3.867e-02,
  358.             5.413e-03,
  359.             -5.289e-04,
  360.             3.229e-04,
  361.             2.067e-05,
  362.             3.000e-01,
  363.             2.031e-02,
  364.             5.900e-03,
  365.             4.573e-04,
  366.             -7.619e-05,
  367.             2.327e-06,
  368.             3.845e-06,
  369.             1.182e-01,
  370.             1.158e-02,
  371.             5.445e-03,
  372.             6.219e-05,
  373.             4.204e-06,
  374.             -2.093e-06,
  375.             1.540e-07,
  376.             -4.280e-08,
  377.             -4.751e-01,
  378.             -3.490e-02,
  379.             1.758e-03,
  380.             4.019e-04,
  381.             -2.799e-06,
  382.             -1.287e-06,
  383.             5.468e-07,
  384.             7.580e-08,
  385.             -6.300e-09,
  386.             -1.160e-01,
  387.             8.301e-03,
  388.             8.771e-04,
  389.             9.955e-05,
  390.             -1.718e-06,
  391.             -2.012e-06,
  392.             1.170e-08,
  393.             1.790e-08,
  394.             -1.300e-09,
  395.             1.000e-10
  396.         };

  397.         /** Mean hydrostatic coefficients b.*/
  398.         private static final double[] BH_MEAN = {
  399.             0.000e+00,
  400.             0.000e+00,
  401.             3.249e-02,
  402.             0.000e+00,
  403.             3.324e-02,
  404.             1.850e-02,
  405.             0.000e+00,
  406.             -1.115e-01,
  407.             2.519e-02,
  408.             4.923e-03,
  409.             0.000e+00,
  410.             2.737e-02,
  411.             1.595e-02,
  412.             -7.332e-04,
  413.             1.933e-04,
  414.             0.000e+00,
  415.             -4.796e-02,
  416.             6.381e-03,
  417.             -1.599e-04,
  418.             -3.685e-04,
  419.             1.815e-05,
  420.             0.000e+00,
  421.             7.033e-02,
  422.             2.426e-03,
  423.             -1.111e-03,
  424.             -1.357e-04,
  425.             -7.828e-06,
  426.             2.547e-06,
  427.             0.000e+00,
  428.             5.779e-03,
  429.             3.133e-03,
  430.             -5.312e-04,
  431.             -2.028e-05,
  432.             2.323e-07,
  433.             -9.100e-08,
  434.             -1.650e-08,
  435.             0.000e+00,
  436.             3.688e-02,
  437.             -8.638e-04,
  438.             -8.514e-05,
  439.             -2.828e-05,
  440.             5.403e-07,
  441.             4.390e-07,
  442.             1.350e-08,
  443.             1.800e-09,
  444.             0.000e+00,
  445.             -2.736e-02,
  446.             -2.977e-04,
  447.             8.113e-05,
  448.             2.329e-07,
  449.             8.451e-07,
  450.             4.490e-08,
  451.             -8.100e-09,
  452.             -1.500e-09,
  453.             2.000e-10
  454.         };

  455.         /** Amplitude for hydrostatic coefficients a.*/
  456.         private static final double[] AH_AMPL = {
  457.             -2.738e-01,
  458.             -2.837e+00,
  459.             1.298e-02,
  460.             -3.588e-01,
  461.             2.413e-02,
  462.             3.427e-02,
  463.             -7.624e-01,
  464.             7.272e-02,
  465.             2.160e-02,
  466.             -3.385e-03,
  467.             4.424e-01,
  468.             3.722e-02,
  469.             2.195e-02,
  470.             -1.503e-03,
  471.             2.426e-04,
  472.             3.013e-01,
  473.             5.762e-02,
  474.             1.019e-02,
  475.             -4.476e-04,
  476.             6.790e-05,
  477.             3.227e-05,
  478.             3.123e-01,
  479.             -3.535e-02,
  480.             4.840e-03,
  481.             3.025e-06,
  482.             -4.363e-05,
  483.             2.854e-07,
  484.             -1.286e-06,
  485.             -6.725e-01,
  486.             -3.730e-02,
  487.             8.964e-04,
  488.             1.399e-04,
  489.             -3.990e-06,
  490.             7.431e-06,
  491.             -2.796e-07,
  492.             -1.601e-07,
  493.             4.068e-02,
  494.             -1.352e-02,
  495.             7.282e-04,
  496.             9.594e-05,
  497.             2.070e-06,
  498.             -9.620e-08,
  499.             -2.742e-07,
  500.             -6.370e-08,
  501.             -6.300e-09,
  502.             8.625e-02,
  503.             -5.971e-03,
  504.             4.705e-04,
  505.             2.335e-05,
  506.             4.226e-06,
  507.             2.475e-07,
  508.             -8.850e-08,
  509.             -3.600e-08,
  510.             -2.900e-09,
  511.             0.000e+00
  512.         };

  513.         /** Amplitude for hydrostatic coefficients b.*/
  514.         private static final double[] BH_AMPL = {
  515.             0.000e+00,
  516.             0.000e+00,
  517.             -1.136e-01,
  518.             0.000e+00,
  519.             -1.868e-01,
  520.             -1.399e-02,
  521.             0.000e+00,
  522.             -1.043e-01,
  523.             1.175e-02,
  524.             -2.240e-03,
  525.             0.000e+00,
  526.             -3.222e-02,
  527.             1.333e-02,
  528.             -2.647e-03,
  529.             -2.316e-05,
  530.             0.000e+00,
  531.             5.339e-02,
  532.             1.107e-02,
  533.             -3.116e-03,
  534.             -1.079e-04,
  535.             -1.299e-05,
  536.             0.000e+00,
  537.             4.861e-03,
  538.             8.891e-03,
  539.             -6.448e-04,
  540.             -1.279e-05,
  541.             6.358e-06,
  542.             -1.417e-07,
  543.             0.000e+00,
  544.             3.041e-02,
  545.             1.150e-03,
  546.             -8.743e-04,
  547.             -2.781e-05,
  548.             6.367e-07,
  549.             -1.140e-08,
  550.             -4.200e-08,
  551.             0.000e+00,
  552.             -2.982e-02,
  553.             -3.000e-03,
  554.             1.394e-05,
  555.             -3.290e-05,
  556.             -1.705e-07,
  557.             7.440e-08,
  558.             2.720e-08,
  559.             -6.600e-09,
  560.             0.000e+00,
  561.             1.236e-02,
  562.             -9.981e-04,
  563.             -3.792e-05,
  564.             -1.355e-05,
  565.             1.162e-06,
  566.             -1.789e-07,
  567.             1.470e-08,
  568.             -2.400e-09,
  569.             -4.000e-10
  570.         };

  571.         /** Mean wet coefficients a.*/
  572.         private static final double[] AW_MEAN = {
  573.             5.640e+01,
  574.             1.555e+00,
  575.             -1.011e+00,
  576.             -3.975e+00,
  577.             3.171e-02,
  578.             1.065e-01,
  579.             6.175e-01,
  580.             1.376e-01,
  581.             4.229e-02,
  582.             3.028e-03,
  583.             1.688e+00,
  584.             -1.692e-01,
  585.             5.478e-02,
  586.             2.473e-02,
  587.             6.059e-04,
  588.             2.278e+00,
  589.             6.614e-03,
  590.             -3.505e-04,
  591.             -6.697e-03,
  592.             8.402e-04,
  593.             7.033e-04,
  594.             -3.236e+00,
  595.             2.184e-01,
  596.             -4.611e-02,
  597.             -1.613e-02,
  598.             -1.604e-03,
  599.             5.420e-05,
  600.             7.922e-05,
  601.             -2.711e-01,
  602.             -4.406e-01,
  603.             -3.376e-02,
  604.             -2.801e-03,
  605.             -4.090e-04,
  606.             -2.056e-05,
  607.             6.894e-06,
  608.             2.317e-06,
  609.             1.941e+00,
  610.             -2.562e-01,
  611.             1.598e-02,
  612.             5.449e-03,
  613.             3.544e-04,
  614.             1.148e-05,
  615.             7.503e-06,
  616.             -5.667e-07,
  617.             -3.660e-08,
  618.             8.683e-01,
  619.             -5.931e-02,
  620.             -1.864e-03,
  621.             -1.277e-04,
  622.             2.029e-04,
  623.             1.269e-05,
  624.             1.629e-06,
  625.             9.660e-08,
  626.             -1.015e-07,
  627.             -5.000e-10
  628.         };

  629.         /** Mean wet coefficients b.*/
  630.         private static final double[] BW_MEAN = {
  631.             0.000e+00,
  632.             0.000e+00,
  633.             2.592e-01,
  634.             0.000e+00,
  635.             2.974e-02,
  636.             -5.471e-01,
  637.             0.000e+00,
  638.             -5.926e-01,
  639.             -1.030e-01,
  640.             -1.567e-02,
  641.             0.000e+00,
  642.             1.710e-01,
  643.             9.025e-02,
  644.             2.689e-02,
  645.             2.243e-03,
  646.             0.000e+00,
  647.             3.439e-01,
  648.             2.402e-02,
  649.             5.410e-03,
  650.             1.601e-03,
  651.             9.669e-05,
  652.             0.000e+00,
  653.             9.502e-02,
  654.             -3.063e-02,
  655.             -1.055e-03,
  656.             -1.067e-04,
  657.             -1.130e-04,
  658.             2.124e-05,
  659.             0.000e+00,
  660.             -3.129e-01,
  661.             8.463e-03,
  662.             2.253e-04,
  663.             7.413e-05,
  664.             -9.376e-05,
  665.             -1.606e-06,
  666.             2.060e-06,
  667.             0.000e+00,
  668.             2.739e-01,
  669.             1.167e-03,
  670.             -2.246e-05,
  671.             -1.287e-04,
  672.             -2.438e-05,
  673.             -7.561e-07,
  674.             1.158e-06,
  675.             4.950e-08,
  676.             0.000e+00,
  677.             -1.344e-01,
  678.             5.342e-03,
  679.             3.775e-04,
  680.             -6.756e-05,
  681.             -1.686e-06,
  682.             -1.184e-06,
  683.             2.768e-07,
  684.             2.730e-08,
  685.             5.700e-09
  686.         };

  687.         /** Amplitude for wet coefficients a.*/
  688.         private static final double[] AW_AMPL = {
  689.             1.023e-01,
  690.             -2.695e+00,
  691.             3.417e-01,
  692.             -1.405e-01,
  693.             3.175e-01,
  694.             2.116e-01,
  695.             3.536e+00,
  696.             -1.505e-01,
  697.             -1.660e-02,
  698.             2.967e-02,
  699.             3.819e-01,
  700.             -1.695e-01,
  701.             -7.444e-02,
  702.             7.409e-03,
  703.             -6.262e-03,
  704.             -1.836e+00,
  705.             -1.759e-02,
  706.             -6.256e-02,
  707.             -2.371e-03,
  708.             7.947e-04,
  709.             1.501e-04,
  710.             -8.603e-01,
  711.             -1.360e-01,
  712.             -3.629e-02,
  713.             -3.706e-03,
  714.             -2.976e-04,
  715.             1.857e-05,
  716.             3.021e-05,
  717.             2.248e+00,
  718.             -1.178e-01,
  719.             1.255e-02,
  720.             1.134e-03,
  721.             -2.161e-04,
  722.             -5.817e-06,
  723.             8.836e-07,
  724.             -1.769e-07,
  725.             7.313e-01,
  726.             -1.188e-01,
  727.             1.145e-02,
  728.             1.011e-03,
  729.             1.083e-04,
  730.             2.570e-06,
  731.             -2.140e-06,
  732.             -5.710e-08,
  733.             2.000e-08,
  734.             -1.632e+00,
  735.             -6.948e-03,
  736.             -3.893e-03,
  737.             8.592e-04,
  738.             7.577e-05,
  739.             4.539e-06,
  740.             -3.852e-07,
  741.             -2.213e-07,
  742.             -1.370e-08,
  743.             5.800e-09
  744.         };

  745.         /** Amplitude for wet coefficients b.*/
  746.         private static final double[] BW_AMPL = {
  747.             0.000e+00,
  748.             0.000e+00,
  749.             -8.865e-02,
  750.             0.000e+00,
  751.             -4.309e-01,
  752.             6.340e-02,
  753.             0.000e+00,
  754.             1.162e-01,
  755.             6.176e-02,
  756.             -4.234e-03,
  757.             0.000e+00,
  758.             2.530e-01,
  759.             4.017e-02,
  760.             -6.204e-03,
  761.             4.977e-03,
  762.             0.000e+00,
  763.             -1.737e-01,
  764.             -5.638e-03,
  765.             1.488e-04,
  766.             4.857e-04,
  767.             -1.809e-04,
  768.             0.000e+00,
  769.             -1.514e-01,
  770.             -1.685e-02,
  771.             5.333e-03,
  772.             -7.611e-05,
  773.             2.394e-05,
  774.             8.195e-06,
  775.             0.000e+00,
  776.             9.326e-02,
  777.             -1.275e-02,
  778.             -3.071e-04,
  779.             5.374e-05,
  780.             -3.391e-05,
  781.             -7.436e-06,
  782.             6.747e-07,
  783.             0.000e+00,
  784.             -8.637e-02,
  785.             -3.807e-03,
  786.             -6.833e-04,
  787.             -3.861e-05,
  788.             -2.268e-05,
  789.             1.454e-06,
  790.             3.860e-07,
  791.             -1.068e-07,
  792.             0.000e+00,
  793.             -2.658e-02,
  794.             -1.947e-03,
  795.             7.131e-04,
  796.             -3.506e-05,
  797.             1.885e-07,
  798.             5.792e-07,
  799.             3.990e-08,
  800.             2.000e-08,
  801.             -5.700e-09
  802.         };

  803.         /** Build a new instance. */
  804.         ABCoefficients() {

  805.         }

  806.         /** Get the value of the mean hydrostatique coefficient ah for the given index.
  807.          * @param index index
  808.          * @return the mean hydrostatique coefficient ah for the given index
  809.          */
  810.         public double getAHMean(final int index) {
  811.             return AH_MEAN[index];
  812.         }

  813.         /** Get the value of the mean hydrostatique coefficient bh for the given index.
  814.          * @param index index
  815.          * @return the mean hydrostatique coefficient bh for the given index
  816.          */
  817.         public double getBHMean(final int index) {
  818.             return BH_MEAN[index];
  819.         }

  820.         /** Get the value of the mean wet coefficient aw for the given index.
  821.          * @param index index
  822.          * @return the mean wet coefficient aw for the given index
  823.          */
  824.         public double getAWMean(final int index) {
  825.             return AW_MEAN[index];
  826.         }

  827.         /** Get the value of the mean wet coefficient bw for the given index.
  828.          * @param index index
  829.          * @return the mean wet coefficient bw for the given index
  830.          */
  831.         public double getBWMean(final int index) {
  832.             return BW_MEAN[index];
  833.         }

  834.         /** Get the value of the amplitude of the hydrostatique coefficient ah for the given index.
  835.          * @param index index
  836.          * @return the amplitude of the hydrostatique coefficient ah for the given index
  837.          */
  838.         public double getAHAmplitude(final int index) {
  839.             return AH_AMPL[index];
  840.         }

  841.         /** Get the value of the amplitude of the hydrostatique coefficient bh for the given index.
  842.          * @param index index
  843.          * @return the amplitude of the hydrostatique coefficient bh for the given index
  844.          */
  845.         public double getBHAmplitude(final int index) {
  846.             return BH_AMPL[index];
  847.         }

  848.         /** Get the value of the amplitude of the wet coefficient aw for the given index.
  849.          * @param index index
  850.          * @return the amplitude of the wet coefficient aw for the given index
  851.          */
  852.         public double getAWAmplitude(final int index) {
  853.             return AW_AMPL[index];
  854.         }

  855.         /** Get the value of the amplitude of the wet coefficient bw for the given index.
  856.          * @param index index
  857.          * @return the amplitude of the wet coefficient bw for the given index
  858.          */
  859.         public double getBWAmplitude(final int index) {
  860.             return BW_AMPL[index];
  861.         }
  862.     }
  863. }