CartesianAdjointDynamicsProviderFactory.java

  1. /* Copyright 2022-2025 Romain Serra
  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.control.indirect.shooting.propagation;

  18. import org.hipparchus.CalculusFieldElement;
  19. import org.hipparchus.Field;
  20. import org.orekit.control.indirect.adjoint.CartesianAdjointDerivativesProvider;
  21. import org.orekit.control.indirect.adjoint.CartesianAdjointEquationTerm;
  22. import org.orekit.control.indirect.adjoint.FieldCartesianAdjointDerivativesProvider;
  23. import org.orekit.control.indirect.adjoint.cost.BoundedCartesianEnergy;
  24. import org.orekit.control.indirect.adjoint.cost.CartesianFlightDurationCost;
  25. import org.orekit.control.indirect.adjoint.cost.CartesianFuelCost;
  26. import org.orekit.control.indirect.adjoint.cost.FieldBoundedCartesianEnergy;
  27. import org.orekit.control.indirect.adjoint.cost.FieldCartesianFlightDurationCost;
  28. import org.orekit.control.indirect.adjoint.cost.FieldCartesianFuelCost;
  29. import org.orekit.control.indirect.adjoint.cost.FieldLogarithmicBarrierCartesianFuel;
  30. import org.orekit.control.indirect.adjoint.cost.FieldQuadraticPenaltyCartesianFuel;
  31. import org.orekit.control.indirect.adjoint.cost.FieldUnboundedCartesianEnergy;
  32. import org.orekit.control.indirect.adjoint.cost.FieldUnboundedCartesianEnergyNeglectingMass;
  33. import org.orekit.control.indirect.adjoint.cost.LogarithmicBarrierCartesianFuel;
  34. import org.orekit.control.indirect.adjoint.cost.QuadraticPenaltyCartesianFuel;
  35. import org.orekit.control.indirect.adjoint.cost.UnboundedCartesianEnergy;
  36. import org.orekit.control.indirect.adjoint.cost.UnboundedCartesianEnergyNeglectingMass;
  37. import org.orekit.propagation.events.EventDetectionSettings;
  38. import org.orekit.propagation.events.FieldEventDetectionSettings;

  39. /**
  40.  * Factory for common Cartesian adjoint dynamics providers.
  41.  *
  42.  * @see AdjointDynamicsProvider
  43.  * @author Romain Serra
  44.  * @since 13.0
  45.  */
  46. public class CartesianAdjointDynamicsProviderFactory {

  47.     /**
  48.      * Private constructor.
  49.      */
  50.     private CartesianAdjointDynamicsProviderFactory() {
  51.         // factory class
  52.     }

  53.     /**
  54.      * Method building a provider with unbounded Cartesian energy and vanishing mass flow as cost.
  55.      * @param adjointName adjoint name
  56.      * @param massFlowRateFactor mass flow rate factor
  57.      * @param maximumThrustMagnitude maximum thrust magnitude
  58.      * @param cartesianAdjointEquationTerms Cartesian adjoint equation terms
  59.      * @return provider
  60.      */
  61.     public static CartesianAdjointDynamicsProvider buildFlightDurationProvider(final String adjointName,
  62.                                                                                final double massFlowRateFactor,
  63.                                                                                final double maximumThrustMagnitude,
  64.                                                                                final CartesianAdjointEquationTerm... cartesianAdjointEquationTerms) {
  65.         return new CartesianAdjointDynamicsProvider(adjointName, getDimension(massFlowRateFactor)) {

  66.             @Override
  67.             public CartesianAdjointDerivativesProvider buildAdditionalDerivativesProvider() {
  68.                 return new CartesianAdjointDerivativesProvider(new CartesianFlightDurationCost(adjointName, massFlowRateFactor, maximumThrustMagnitude),
  69.                         cartesianAdjointEquationTerms);
  70.             }

  71.             @Override
  72.             public <T extends CalculusFieldElement<T>> FieldCartesianAdjointDerivativesProvider<T> buildFieldAdditionalDerivativesProvider(final Field<T> field) {
  73.                 return new FieldCartesianAdjointDerivativesProvider<>(new FieldCartesianFlightDurationCost<>(adjointName,
  74.                         field.getZero().newInstance(massFlowRateFactor), field.getZero().newInstance(maximumThrustMagnitude)),
  75.                         cartesianAdjointEquationTerms);
  76.             }
  77.         };
  78.     }

  79.     /**
  80.      * Method building a provider with unbounded Cartesian energy and vanishing mass flow as cost.
  81.      * @param adjointName adjoint name
  82.      * @param cartesianAdjointEquationTerms Cartesian adjoint equation terms
  83.      * @return provider
  84.      */
  85.     public static CartesianAdjointDynamicsProvider buildUnboundedEnergyProviderNeglectingMass(final String adjointName,
  86.                                                                                               final CartesianAdjointEquationTerm... cartesianAdjointEquationTerms) {
  87.         return new CartesianAdjointDynamicsProvider(adjointName, 6) {

  88.             @Override
  89.             public CartesianAdjointDerivativesProvider buildAdditionalDerivativesProvider() {
  90.                 return new CartesianAdjointDerivativesProvider(new UnboundedCartesianEnergyNeglectingMass(adjointName),
  91.                         cartesianAdjointEquationTerms);
  92.             }

  93.             @Override
  94.             public <T extends CalculusFieldElement<T>> FieldCartesianAdjointDerivativesProvider<T> buildFieldAdditionalDerivativesProvider(final Field<T> field) {
  95.                 return new FieldCartesianAdjointDerivativesProvider<>(new FieldUnboundedCartesianEnergyNeglectingMass<>(adjointName, field),
  96.                         cartesianAdjointEquationTerms);
  97.             }
  98.         };
  99.     }

  100.     /**
  101.      * Method building a provider with unbounded Cartesian energy as cost.
  102.      * @param adjointName adjoint name
  103.      * @param massFlowRateFactor mass flow rate factor
  104.      * @param eventDetectionSettings detection settings for adjoint-related events
  105.      * @param cartesianAdjointEquationTerms Cartesian adjoint equation terms
  106.      * @return provider
  107.      */
  108.     public static CartesianAdjointDynamicsProvider buildUnboundedEnergyProvider(final String adjointName,
  109.                                                                                 final double massFlowRateFactor,
  110.                                                                                 final EventDetectionSettings eventDetectionSettings,
  111.                                                                                 final CartesianAdjointEquationTerm... cartesianAdjointEquationTerms) {
  112.         return new CartesianAdjointDynamicsProvider(adjointName, getDimension(massFlowRateFactor)) {

  113.             @Override
  114.             public CartesianAdjointDerivativesProvider buildAdditionalDerivativesProvider() {
  115.                 return new CartesianAdjointDerivativesProvider(new UnboundedCartesianEnergy(adjointName,
  116.                         massFlowRateFactor, eventDetectionSettings), cartesianAdjointEquationTerms);
  117.             }

  118.             @Override
  119.             public <T extends CalculusFieldElement<T>> FieldCartesianAdjointDerivativesProvider<T> buildFieldAdditionalDerivativesProvider(final Field<T> field) {
  120.                 return new FieldCartesianAdjointDerivativesProvider<>(new FieldUnboundedCartesianEnergy<>(adjointName,
  121.                         field.getZero().newInstance(massFlowRateFactor), new FieldEventDetectionSettings<>(field,
  122.                         eventDetectionSettings)), cartesianAdjointEquationTerms);
  123.             }
  124.         };
  125.     }

  126.     /**
  127.      * Method building a provider with bounded Cartesian energy as cost.
  128.      * @param adjointName adjoint name
  129.      * @param massFlowRateFactor mass flow rate factor
  130.      * @param maximumThrustMagnitude maximum thrust magnitude
  131.      * @param eventDetectionSettings detection settings for adjoint-related events
  132.      * @param cartesianAdjointEquationTerms Cartesian adjoint equation terms
  133.      * @return provider
  134.      */
  135.     public static CartesianAdjointDynamicsProvider buildBoundedEnergyProvider(final String adjointName,
  136.                                                                               final double massFlowRateFactor,
  137.                                                                               final double maximumThrustMagnitude,
  138.                                                                               final EventDetectionSettings eventDetectionSettings,
  139.                                                                               final CartesianAdjointEquationTerm... cartesianAdjointEquationTerms) {
  140.         return new CartesianAdjointDynamicsProvider(adjointName, getDimension(massFlowRateFactor)) {

  141.             @Override
  142.             public CartesianAdjointDerivativesProvider buildAdditionalDerivativesProvider() {
  143.                 return new CartesianAdjointDerivativesProvider(new BoundedCartesianEnergy(adjointName, massFlowRateFactor,
  144.                         maximumThrustMagnitude, eventDetectionSettings), cartesianAdjointEquationTerms);
  145.             }

  146.             @Override
  147.             public <T extends CalculusFieldElement<T>> FieldCartesianAdjointDerivativesProvider<T> buildFieldAdditionalDerivativesProvider(final Field<T> field) {
  148.                 final T zero = field.getZero();
  149.                 return new FieldCartesianAdjointDerivativesProvider<>(new FieldBoundedCartesianEnergy<>(adjointName,
  150.                         zero.newInstance(massFlowRateFactor), zero.newInstance(maximumThrustMagnitude),
  151.                         new FieldEventDetectionSettings<>(field, eventDetectionSettings)), cartesianAdjointEquationTerms);
  152.             }
  153.         };
  154.     }

  155.     /**
  156.      * Method building a provider with bounded Cartesian fuel as cost.
  157.      * @param adjointName adjoint name
  158.      * @param massFlowRateFactor mass flow rate factor
  159.      * @param maximumThrustMagnitude maximum thrust magnitude
  160.      * @param eventDetectionSettings detection settings for adjoint-related events
  161.      * @param cartesianAdjointEquationTerms Cartesian adjoint equation terms
  162.      * @return provider
  163.      */
  164.     public static CartesianAdjointDynamicsProvider buildBoundedFuelCostProvider(final String adjointName,
  165.                                                                                 final double massFlowRateFactor,
  166.                                                                                 final double maximumThrustMagnitude,
  167.                                                                                 final EventDetectionSettings eventDetectionSettings,
  168.                                                                                 final CartesianAdjointEquationTerm... cartesianAdjointEquationTerms) {
  169.         return new CartesianAdjointDynamicsProvider(adjointName, getDimension(massFlowRateFactor)) {

  170.             @Override
  171.             public CartesianAdjointDerivativesProvider buildAdditionalDerivativesProvider() {
  172.                 return new CartesianAdjointDerivativesProvider(new CartesianFuelCost(adjointName, massFlowRateFactor,
  173.                         maximumThrustMagnitude, eventDetectionSettings), cartesianAdjointEquationTerms);
  174.             }

  175.             @Override
  176.             public <T extends CalculusFieldElement<T>> FieldCartesianAdjointDerivativesProvider<T> buildFieldAdditionalDerivativesProvider(final Field<T> field) {
  177.                 final T zero = field.getZero();
  178.                 return new FieldCartesianAdjointDerivativesProvider<>(new FieldCartesianFuelCost<>(adjointName,
  179.                         zero.newInstance(massFlowRateFactor), zero.newInstance(maximumThrustMagnitude),
  180.                         new FieldEventDetectionSettings<>(field, eventDetectionSettings)), cartesianAdjointEquationTerms);
  181.             }
  182.         };
  183.     }

  184.     /**
  185.      * Method building a provider with bounded Cartesian fuel penalized with a quadratic term.
  186.      * @param adjointName adjoint name
  187.      * @param massFlowRateFactor mass flow rate factor
  188.      * @param maximumThrustMagnitude maximum thrust magnitude
  189.      * @param epsilon penalty weight
  190.      * @param eventDetectionSettings detection settings for adjoint-related events
  191.      * @param cartesianAdjointEquationTerms Cartesian adjoint equation terms
  192.      * @return provider
  193.      */
  194.     public static CartesianAdjointDynamicsProvider buildQuadraticPenaltyFuelCostProvider(final String adjointName,
  195.                                                                                          final double massFlowRateFactor,
  196.                                                                                          final double maximumThrustMagnitude,
  197.                                                                                          final double epsilon,
  198.                                                                                          final EventDetectionSettings eventDetectionSettings,
  199.                                                                                          final CartesianAdjointEquationTerm... cartesianAdjointEquationTerms) {
  200.         return new CartesianAdjointDynamicsProvider(adjointName, getDimension(massFlowRateFactor)) {

  201.             @Override
  202.             public CartesianAdjointDerivativesProvider buildAdditionalDerivativesProvider() {
  203.                 return new CartesianAdjointDerivativesProvider(new QuadraticPenaltyCartesianFuel(adjointName, massFlowRateFactor,
  204.                         maximumThrustMagnitude, epsilon, eventDetectionSettings), cartesianAdjointEquationTerms);
  205.             }

  206.             @Override
  207.             public <T extends CalculusFieldElement<T>> FieldCartesianAdjointDerivativesProvider<T> buildFieldAdditionalDerivativesProvider(final Field<T> field) {
  208.                 final T zero = field.getZero();
  209.                 return new FieldCartesianAdjointDerivativesProvider<>(new FieldQuadraticPenaltyCartesianFuel<>(adjointName,
  210.                         zero.newInstance(massFlowRateFactor), zero.newInstance(maximumThrustMagnitude),
  211.                         zero.newInstance(epsilon), new FieldEventDetectionSettings<>(field, eventDetectionSettings)),
  212.                         cartesianAdjointEquationTerms);
  213.             }
  214.         };
  215.     }

  216.     /**
  217.      * Method building a provider with bounded Cartesian fuel penalized with a logarithmic barrier.
  218.      * @param adjointName adjoint name
  219.      * @param massFlowRateFactor mass flow rate factor
  220.      * @param maximumThrustMagnitude maximum thrust magnitude
  221.      * @param epsilon penalty weight
  222.      * @param cartesianAdjointEquationTerms Cartesian adjoint equation terms
  223.      * @return provider
  224.      */
  225.     public static CartesianAdjointDynamicsProvider buildLogarithmicBarrierFuelCostProvider(final String adjointName,
  226.                                                                                            final double massFlowRateFactor,
  227.                                                                                            final double maximumThrustMagnitude,
  228.                                                                                            final double epsilon,
  229.                                                                                            final CartesianAdjointEquationTerm... cartesianAdjointEquationTerms) {
  230.         return new CartesianAdjointDynamicsProvider(adjointName, getDimension(massFlowRateFactor)) {

  231.             @Override
  232.             public CartesianAdjointDerivativesProvider buildAdditionalDerivativesProvider() {
  233.                 return new CartesianAdjointDerivativesProvider(new LogarithmicBarrierCartesianFuel(adjointName, massFlowRateFactor,
  234.                         maximumThrustMagnitude, epsilon), cartesianAdjointEquationTerms);
  235.             }

  236.             @Override
  237.             public <T extends CalculusFieldElement<T>> FieldCartesianAdjointDerivativesProvider<T> buildFieldAdditionalDerivativesProvider(final Field<T> field) {
  238.                 final T zero = field.getZero();
  239.                 return new FieldCartesianAdjointDerivativesProvider<>(new FieldLogarithmicBarrierCartesianFuel<>(adjointName,
  240.                         zero.newInstance(massFlowRateFactor), zero.newInstance(maximumThrustMagnitude),
  241.                         zero.newInstance(epsilon)), cartesianAdjointEquationTerms);
  242.             }
  243.         };
  244.     }

  245.     /**
  246.      * Get the adjoint dimension.
  247.      * @param massFlowRateFactor mass flow rate factor
  248.      * @return dimension
  249.      */
  250.     private static int getDimension(final double massFlowRateFactor) {
  251.         return massFlowRateFactor == 0. ? 6 : 7;
  252.     }
  253. }