1   /* Copyright 2002-2025 CS GROUP
2    * Licensed to CS GROUP (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.estimation.measurements.modifiers;
18  
19  import java.util.ArrayList;
20  import java.util.List;
21  
22  import org.hipparchus.stat.descriptive.DescriptiveStatistics;
23  import org.junit.jupiter.api.Assertions;
24  import org.junit.jupiter.api.Test;
25  import org.orekit.estimation.Context;
26  import org.orekit.estimation.EstimationTestUtils;
27  import org.orekit.estimation.measurements.EstimatedMeasurementBase;
28  import org.orekit.estimation.measurements.EstimationModifier;
29  import org.orekit.estimation.measurements.ObservedMeasurement;
30  import org.orekit.estimation.measurements.Range;
31  import org.orekit.estimation.measurements.TwoWayRangeMeasurementCreator;
32  import org.orekit.orbits.OrbitType;
33  import org.orekit.orbits.PositionAngleType;
34  import org.orekit.propagation.Propagator;
35  import org.orekit.propagation.SpacecraftState;
36  import org.orekit.propagation.conversion.NumericalPropagatorBuilder;
37  import org.orekit.time.AbsoluteDate;
38  
39  public class ShapiroRangeModifierTest {
40  
41      @Test
42      public void testShapiroOneWay() {
43          doTestShapiro(false, 0.006850703, 0.008320738, 0.010297508);
44      }
45  
46      @Test
47      public void testShapiroTwoWay() {
48          doTestShapiro(true, 0.006850703, 0.008320739, 0.010297503);
49      }
50  
51      private void doTestShapiro(final boolean twoWay,
52                                 final double expectedMin, final double expectedMean, final double expectedMax) {
53  
54          Context context = EstimationTestUtils.eccentricContext("regular-data:potential:tides");
55  
56          final NumericalPropagatorBuilder propagatorBuilder =
57                          context.createBuilder(OrbitType.KEPLERIAN, PositionAngleType.TRUE, true,
58                                                1.0e-6, 60.0, 0.001);
59  
60          // create perfect range measurements
61          final Propagator propagator = EstimationTestUtils.createPropagator(context.initialOrbit,
62                                                                             propagatorBuilder);
63          List<ObservedMeasurement<?>> measurements =
64                          EstimationTestUtils.createMeasurements(propagator,
65                                                                 new TwoWayRangeMeasurementCreator(context),
66                                                                 1.0, 3.0, 300.0);
67          if (!twoWay) {
68              // convert default two way measurements to one way measurements
69              final List<ObservedMeasurement<?>> converted = new ArrayList<>();
70              for (final ObservedMeasurement<?> m : measurements) {
71                  final Range range = (Range) m;
72                  converted.add(new Range(range.getStation(), false, range.getDate(),
73                                          range.getObservedValue()[0],
74                                          range.getTheoreticalStandardDeviation()[0],
75                                          range.getBaseWeight()[0],
76                                          range.getSatellites().get(0)));
77              }
78              measurements = converted;
79          }
80          propagator.clearStepHandlers();
81  
82  
83          final ShapiroRangeModifier modifier = new ShapiroRangeModifier(context.initialOrbit.getMu());
84  
85          DescriptiveStatistics stat = new DescriptiveStatistics();
86          for (final ObservedMeasurement<?> measurement : measurements) {
87              final AbsoluteDate date = measurement.getDate();
88  
89              final SpacecraftState refstate = propagator.propagate(date);
90  
91              Range range = (Range) measurement;
92              EstimatedMeasurementBase<Range> evalNoMod = range.estimateWithoutDerivatives(12, 17, new SpacecraftState[] { refstate });
93              Assertions.assertEquals(12, evalNoMod.getIteration());
94              Assertions.assertEquals(17, evalNoMod.getCount());
95  
96              // add modifier
97              range.addModifier(modifier);
98              boolean found = false;
99              for (final EstimationModifier<Range> existing : range.getModifiers()) {
100                 found = found || existing == modifier;
101             }
102             Assertions.assertTrue(found);
103             EstimatedMeasurementBase<Range> eval = range.estimateWithoutDerivatives( new SpacecraftState[] { refstate });
104 
105             stat.addValue(eval.getEstimatedValue()[0] - evalNoMod.getEstimatedValue()[0]);
106             Assertions.assertEquals(1,
107                                     eval.getAppliedEffects().entrySet().stream().
108                                     filter(e -> e.getKey().getEffectName().equals("Shapiro")).count());
109 
110         }
111 
112         Assertions.assertEquals(expectedMin,  stat.getMin(),  1.0e-9);
113         Assertions.assertEquals(expectedMean, stat.getMean(), 1.0e-9);
114         Assertions.assertEquals(expectedMax,  stat.getMax(),  1.0e-9);
115 
116     }
117 
118 }
119 
120