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 org.hipparchus.complex.Complex;
21  import org.hipparchus.ode.nonstiff.LutherIntegrator;
22  import org.hipparchus.util.FastMath;
23  import org.junit.Assert;
24  import org.junit.Test;
25  
26  
27  public class ComplexODEConverterTest {
28  
29      @Test
30      public void testDoubleDimension() {
31          ComplexODEConverter converter = new ComplexODEConverter();
32          for (int i = 1; i < 10; ++i) {
33              Assert.assertEquals(2 * i, converter.convertEquations(new Circle(i, 0.2)).getDimension());
34          }
35      }
36  
37      @Test
38      public void testPrimaryEquation() {
39          final double omega = 0.2;
40          ComplexODEConverter converter = new ComplexODEConverter();
41          ComplexOrdinaryDifferentialEquation circle = new Circle(1, omega);
42          ComplexODEState initial = new ComplexODEState(0.0, new Complex[] { Complex.ONE });
43          ComplexODEStateAndDerivative der = new ComplexODEStateAndDerivative(initial.getTime(),
44                                                                              initial.getPrimaryState(),
45                                                                              circle.computeDerivatives(initial.getTime(),
46                                                                                                        initial.getPrimaryState()));
47          Assert.assertEquals(initial.getTime(), der.getTime(), 1.0e-15);
48          Assert.assertEquals(initial.getPrimaryState()[0], der.getPrimaryState()[0]);
49          Assert.assertEquals(initial.getPrimaryState()[0], der.getCompleteState()[0]);
50          Assert.assertEquals(initial.getPrimaryState()[0].multiply(((Circle) circle).iOmega),
51                              der.getSecondaryDerivative(0)[0]);
52          Assert.assertEquals(initial.getPrimaryState()[0].multiply(((Circle) circle).iOmega),
53                              der.getCompleteDerivative()[0]);
54          LutherIntegrator integrator = new LutherIntegrator(1.0e-3);
55          final ComplexODEStateAndDerivative finalstate =
56                          converter.convertState(integrator.integrate(converter.convertEquations(circle),
57                                                                      converter.convertState(initial),
58                                                                      FastMath.PI / omega));
59          Assert.assertEquals(0, finalstate.getNumberOfSecondaryStates());
60          Assert.assertEquals(1, finalstate.getPrimaryStateDimension());
61          Assert.assertEquals(FastMath.PI / omega, finalstate.getTime(),                                1.0e-15);
62          Assert.assertEquals(-1.0,                finalstate.getPrimaryState()[0].getReal(),           1.0e-12);
63          Assert.assertEquals( 0.0,                finalstate.getPrimaryState()[0].getImaginary(),      1.0e-12);
64          Assert.assertEquals( 0.0,                finalstate.getPrimaryDerivative()[0].getReal(),      1.0e-12);
65          Assert.assertEquals(-omega,              finalstate.getPrimaryDerivative()[0].getImaginary(), 1.0e-12);
66      }
67  
68      @Test
69      public void testSecondaryEquation() {
70          final double omegaP  = 0.2;
71          final double omegaS0 = omegaP * 0.5;
72          final double omegaS1 = omegaP * 2;
73          ComplexODEConverter converter = new ComplexODEConverter();
74          ComplexOrdinaryDifferentialEquation primary    = new Circle(1, omegaP);
75          ComplexSecondaryODE                 secondary0 = new Circle(1, omegaS0);
76          ComplexSecondaryODE                 secondary1 = new Circle(1, omegaS1);
77          ExpandableODE expandable = new ExpandableODE(converter.convertEquations(primary));
78          expandable.addSecondaryEquations(converter.convertSecondaryEquations(secondary0));
79          expandable.addSecondaryEquations(converter.convertSecondaryEquations(secondary1));
80          ComplexODEState initial = new ComplexODEState(0.0, new Complex[] { Complex.ONE },
81                                                        new Complex[][] {
82                                                            { Complex.ONE },
83                                                            { Complex.ONE }
84                                                        });
85          ComplexODEStateAndDerivative der = new ComplexODEStateAndDerivative(initial.getTime(),
86                                                                              initial.getPrimaryState(),
87                                                                              primary.computeDerivatives(initial.getTime(),
88                                                                                                        initial.getPrimaryState()),
89                                                                              new Complex[][] {
90                                                                                  initial.getSecondaryState(0),
91                                                                                  initial.getSecondaryState(1)
92                                                                              },
93                                                                              new Complex[][] {
94                                                                                  secondary0.computeDerivatives(initial.getTime(),
95                                                                                                                initial.getPrimaryState(),
96                                                                                                                primary.computeDerivatives(initial.getTime(),
97                                                                                                                                           initial.getPrimaryState()),
98                                                                                                                initial.getSecondaryState(0)),
99                                                                                  secondary1.computeDerivatives(initial.getTime(),
100                                                                                                               initial.getPrimaryState(),
101                                                                                                               primary.computeDerivatives(initial.getTime(),
102                                                                                                                                          initial.getPrimaryState()),
103                                                                                                               initial.getSecondaryState(1))
104                                                                             });
105         Assert.assertEquals(initial.getTime(), der.getTime(), 1.0e-15);
106         Assert.assertEquals(initial.getPrimaryState()[0], der.getPrimaryState()[0]);
107         Assert.assertEquals(initial.getPrimaryState()[0], der.getCompleteState()[0]);
108         Assert.assertEquals(initial.getSecondaryState(0)[0], der.getCompleteState()[1]);
109         Assert.assertEquals(initial.getSecondaryState(1)[0], der.getCompleteState()[2]);
110         Assert.assertEquals(initial.getPrimaryState()[0].multiply(((Circle) primary).iOmega),
111                             der.getSecondaryDerivative(0)[0]);
112         Assert.assertEquals(initial.getPrimaryState()[0].multiply(((Circle) primary).iOmega),
113                             der.getCompleteDerivative()[0]);
114         Assert.assertEquals(initial.getSecondaryState(0)[0].multiply(((Circle) secondary0).iOmega),
115                             der.getCompleteDerivative()[1]);
116         Assert.assertEquals(initial.getSecondaryState(1)[0].multiply(((Circle) secondary1).iOmega),
117                             der.getCompleteDerivative()[2]);
118         LutherIntegrator integrator = new LutherIntegrator(1.0e-3);
119         final ComplexODEStateAndDerivative finalstate =
120                         converter.convertState(integrator.integrate(expandable,
121                                                                     converter.convertState(initial),
122                                                                     FastMath.PI / omegaP));
123         Assert.assertEquals(2, finalstate.getNumberOfSecondaryStates());
124         Assert.assertEquals(1, finalstate.getPrimaryStateDimension());
125         Assert.assertEquals(FastMath.PI / omegaP, finalstate.getTime(),                                   1.0e-15);
126         Assert.assertEquals(-1.0,                 finalstate.getPrimaryState()[0].getReal(),              1.0e-12);
127         Assert.assertEquals( 0.0,                 finalstate.getPrimaryState()[0].getImaginary(),         1.0e-12);
128         Assert.assertEquals( 0.0,                 finalstate.getPrimaryDerivative()[0].getReal(),         1.0e-12);
129         Assert.assertEquals(-omegaP,              finalstate.getPrimaryDerivative()[0].getImaginary(),    1.0e-12);
130         Assert.assertEquals( 0.0,                 finalstate.getSecondaryState(1)[0].getReal(),           1.0e-12);
131         Assert.assertEquals( 1.0,                 finalstate.getSecondaryState(1)[0].getImaginary(),      1.0e-12);
132         Assert.assertEquals(-omegaS0,             finalstate.getSecondaryDerivative(1)[0].getReal(),      1.0e-12);
133         Assert.assertEquals( 0.0,                 finalstate.getSecondaryDerivative(1)[0].getImaginary(), 1.0e-12);
134         Assert.assertEquals( 1.0,                 finalstate.getSecondaryState(2)[0].getReal(),           1.0e-12);
135         Assert.assertEquals( 0.0,                 finalstate.getSecondaryState(2)[0].getImaginary(),      2.0e-12);
136         Assert.assertEquals( 0.0,                 finalstate.getSecondaryDerivative(2)[0].getReal(),      1.0e-12);
137         Assert.assertEquals( omegaS1,             finalstate.getSecondaryDerivative(2)[0].getImaginary(), 1.0e-12);
138     }
139 
140     private static class Circle
141         implements ComplexOrdinaryDifferentialEquation, ComplexSecondaryODE {
142 
143         private int n;
144         private Complex iOmega;
145 
146         public Circle(int n, double omega) {
147             this.n     = n;
148             this.iOmega = new Complex(0.0, omega);
149         }
150 
151         public int getDimension() {
152             return n;
153         }
154 
155         public Complex[] computeDerivatives(double t, Complex[] y) {
156             final Complex[] yDot = new Complex[y.length];
157             for (int i = 0; i < yDot.length; ++i) {
158                 yDot[i] = iOmega.multiply(y[i]);
159             }
160             return yDot;
161         }
162 
163         public Complex[] computeDerivatives(double t, Complex[] primary, Complex[] primaryDot, Complex[] secondary) {
164             return computeDerivatives(t, secondary);
165         }
166 
167     }
168 
169 }