View Javadoc
1   /*
2    * Licensed to the Hipparchus project under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The Hipparchus project 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    *      https://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  
18  package org.hipparchus.ode;
19  
20  import java.io.Serializable;
21  
22  import org.hipparchus.complex.Complex;
23  
24  /** Container for time, main and secondary state vectors.
25  
26   * @see ComplexOrdinaryDifferentialEquation
27   * @see SecondaryODE
28   * @see ODEIntegrator
29   * @see ODEStateAndDerivative
30   * @since 1.4
31   */
32  
33  public class ComplexODEState implements Serializable {
34  
35      /** Serializable UID. */
36      private static final long serialVersionUID = 20180902;
37  
38      /** Time. */
39      private final double time;
40  
41      /** Primary state at time. */
42      private final Complex[] primaryState;
43  
44      /** Secondary state at time. */
45      private final Complex[][] secondaryState;
46  
47      /** Complete dimension. */
48      private final int completeDimension;
49  
50      /** Simple constructor.
51       * <p>Calling this constructor is equivalent to call {@link
52       * #ComplexODEState(double, Complex[], Complex[][])
53       * ComplexODEState(time, state, null)}.</p>
54       * @param time time
55       * @param primaryState primary state at time
56       */
57      public ComplexODEState(double time, Complex[] primaryState) {
58          this(time, primaryState, null);
59      }
60  
61      /** Simple constructor.
62       * @param time time
63       * @param primaryState state at time
64       * @param secondaryState primary state at time (may be null)
65       */
66      public ComplexODEState(double time, Complex[] primaryState, Complex[][] secondaryState) {
67  
68          this.time           = time;
69          this.primaryState   = primaryState.clone();
70          this.secondaryState = copy(secondaryState);
71  
72          // compute once and for all the complete dimension
73          int dimension = primaryState.length;
74          if (secondaryState != null) {
75              for (final Complex[] secondary : secondaryState) {
76                  dimension += secondary.length;
77              }
78          }
79          this.completeDimension = dimension;
80  
81      }
82  
83      /** Copy a two-dimensions array.
84       * @param original original array (may be null)
85       * @return copied array or null if original array was null
86       */
87      protected Complex[][] copy(final Complex[][] original) {
88  
89          // special handling of null arrays
90          if (original == null) {
91              return null; // NOPMD
92          }
93  
94          // allocate the array
95          final Complex[][] copied = new Complex[original.length][];
96  
97          // copy content
98          for (int i = 0; i < original.length; ++i) {
99              copied[i] = original[i].clone();
100         }
101 
102         return copied;
103 
104     }
105 
106     /** Get time.
107      * @return time
108      */
109     public double getTime() {
110         return time;
111     }
112 
113     /** Get primary state dimension.
114      * @return primary state dimension
115      * @see #getSecondaryStateDimension(int)
116      * @see #getCompleteStateDimension()
117      */
118     public int getPrimaryStateDimension() {
119         return primaryState.length;
120     }
121 
122     /** Get primary state at time.
123      * @return primary state at time
124      * @see #getSecondaryState(int)
125      * @see #getCompleteState()
126      */
127     public Complex[] getPrimaryState() {
128         return primaryState.clone();
129     }
130 
131     /** Get the number of secondary states.
132      * @return number of secondary states.
133      */
134     public int getNumberOfSecondaryStates() {
135         return secondaryState == null ? 0 : secondaryState.length;
136     }
137 
138     /** Get secondary state dimension.
139      * @param index index of the secondary set as returned
140      * by {@link ExpandableODE#addSecondaryEquations(SecondaryODE)}
141      * (beware index 0 corresponds to primary state, secondary states start at 1)
142      * @return secondary state dimension
143      * @see #getPrimaryStateDimension()
144      * @see #getCompleteStateDimension()
145      */
146     public int getSecondaryStateDimension(final int index) {
147         return index == 0 ? primaryState.length : secondaryState[index - 1].length;
148     }
149 
150     /** Get secondary state at time.
151      * @param index index of the secondary set as returned
152      * by {@link ExpandableODE#addSecondaryEquations(SecondaryODE)}
153      * (beware index 0 corresponds to primary state, secondary states start at 1)
154      * @return secondary state at time
155      * @see #getPrimaryState()
156      * @see #getCompleteState()
157      */
158     public Complex[] getSecondaryState(final int index) {
159         return index == 0 ? primaryState.clone() : secondaryState[index - 1].clone();
160     }
161 
162     /** Return the dimension of the complete set of equations.
163      * <p>
164      * The complete set of equations correspond to the primary set plus all secondary sets.
165      * </p>
166      * @return dimension of the complete set of equations
167      * @see #getPrimaryStateDimension()
168      * @see #getSecondaryStateDimension(int)
169      */
170     public int getCompleteStateDimension() {
171         return completeDimension;
172     }
173 
174     /** Get complete state at time.
175      * @return complete state at time, starting with
176      * {@link #getPrimaryState() primary state}, followed
177      * by all {@link #getSecondaryState(int) secondary states} in
178      * increasing index order
179      * @see #getPrimaryState()
180      * @see #getSecondaryState(int)
181      */
182     public Complex[] getCompleteState() {
183         final Complex[] completeState = new Complex[getCompleteStateDimension()];
184         System.arraycopy(primaryState, 0, completeState, 0, primaryState.length);
185         int offset = primaryState.length;
186         if (secondaryState != null) {
187             for (int index = 0; index < secondaryState.length; ++index) {
188                 System.arraycopy(secondaryState[index], 0,
189                                  completeState, offset,
190                                  secondaryState[index].length);
191                 offset += secondaryState[index].length;
192             }
193         }
194         return completeState;
195     }
196 
197 }