commons-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From l..@apache.org
Subject svn commit: r729639 - in /commons/proper/math/trunk: ./ src/java/org/apache/commons/math/ src/java/org/apache/commons/math/complex/ src/site/xdoc/ src/test/org/apache/commons/math/complex/
Date Sat, 27 Dec 2008 16:23:43 GMT
Author: luc
Date: Sat Dec 27 08:23:43 2008
New Revision: 729639

URL: http://svn.apache.org/viewvc?rev=729639&view=rev
Log:
added nth root computation for complex numbers
JIRA: MATH-236

Modified:
    commons/proper/math/trunk/pom.xml
    commons/proper/math/trunk/src/java/org/apache/commons/math/MessagesResources_fr.java
    commons/proper/math/trunk/src/java/org/apache/commons/math/complex/Complex.java
    commons/proper/math/trunk/src/site/xdoc/changes.xml
    commons/proper/math/trunk/src/test/org/apache/commons/math/complex/ComplexTest.java

Modified: commons/proper/math/trunk/pom.xml
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/pom.xml?rev=729639&r1=729638&r2=729639&view=diff
==============================================================================
--- commons/proper/math/trunk/pom.xml (original)
+++ commons/proper/math/trunk/pom.xml Sat Dec 27 08:23:43 2008
@@ -118,6 +118,9 @@
       <name>Ken Geis</name>
     </contributor>
     <contributor>
+      <name>Bernhard Gr&#252;newaldt</name>
+    </contributor>
+    <contributor>
       <name>Elliotte Rusty Harold</name>
     </contributor>
     <contributor>

Modified: commons/proper/math/trunk/src/java/org/apache/commons/math/MessagesResources_fr.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/java/org/apache/commons/math/MessagesResources_fr.java?rev=729639&r1=729638&r2=729639&view=diff
==============================================================================
--- commons/proper/math/trunk/src/java/org/apache/commons/math/MessagesResources_fr.java (original)
+++ commons/proper/math/trunk/src/java/org/apache/commons/math/MessagesResources_fr.java Sat
Dec 27 08:23:43 2008
@@ -233,6 +233,10 @@
    { "URL {0} contains no data",
      "l''adresse {0} ne contient aucune donn\u00e9e" },
 
+   // org.apache.commons.math.complex.Complex
+   { "cannot compute nth root for null or negative n: {0}",
+     "impossible de calculer la racine ni\u00e8me pour n n\u00e9gatif ou nul : {0}" },
+
    // org.apache.commons.math.complex.ComplexFormat
    { "unparseable complex number: \"{0}\"",
      "\u00e9chec d''analyse du nombre complexe \"{0}\"" },

Modified: commons/proper/math/trunk/src/java/org/apache/commons/math/complex/Complex.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/java/org/apache/commons/math/complex/Complex.java?rev=729639&r1=729638&r2=729639&view=diff
==============================================================================
--- commons/proper/math/trunk/src/java/org/apache/commons/math/complex/Complex.java (original)
+++ commons/proper/math/trunk/src/java/org/apache/commons/math/complex/Complex.java Sat Dec
27 08:23:43 2008
@@ -18,6 +18,10 @@
 package org.apache.commons.math.complex;
 
 import java.io.Serializable;
+import java.util.ArrayList;
+import java.util.Collection;
+
+import org.apache.commons.math.MathRuntimeException;
 import org.apache.commons.math.util.MathUtils;
 
 /**
@@ -859,6 +863,55 @@
         
         return createComplex(MathUtils.sinh(real2) / d, Math.sin(imaginary2) / d);
     }
+    
+    
+    
+    /**
+     * Compute the angle phi of this complex number.
+     * @return the angle phi of this complex number
+     */
+    public double getPhi() {
+        return Math.atan2(getImaginary(), getReal());
+    }
+    
+    /**
+     * Compute the n-th root of this complex number.
+     * <p>
+     * For a given n it implements the formula: <pre>
+     * <code> z_k = pow( abs , 1.0/n ) * (cos(phi + k * 2&pi;) + i * (sin(phi +
k * 2&pi;)</code></pre></p>
+     * with <i><code>k=0, 1, ..., n-1</code></i> and <i><code>pow(abs,
1.0 / n)</code></i> is the nth root of the absolute-value.
+     * <p>
+     * 
+     * @param n degree of root
+     * @return Collection<Complex> all nth roots of this complex number as a Collection
+     * @throws IllegalArgumentException if parameter n is negative
+     * @since 2.0
+     */
+    public Collection<Complex> nthRoot(int n) throws IllegalArgumentException {
+
+        if (n <= 0) {
+            throw MathRuntimeException.createIllegalArgumentException("cannot compute nth
root for null or negative n: {0}",
+                    new Object[] { n });
+        }
+
+        Collection<Complex> result = new ArrayList<Complex>();
+
+        // nth root of abs
+        final double nthRootOfAbs = Math.pow(abs(), 1.0 / n);
+
+        // Compute nth roots of complex number with k = 0, 1, ... n-1
+        final double phi = getPhi();
+        for (int k = 0; k < n ; k++) {
+            // inner part
+            final double innerPart     = (phi + k * 2 * Math.PI) / n;
+            final double realPart      = nthRootOfAbs *  Math.cos(innerPart);
+            final double imaginaryPart = nthRootOfAbs *  Math.sin(innerPart);
+            result.add(createComplex(realPart, imaginaryPart));
+        }
+
+        return result;
+
+    }
 
     /**
      * Create a complex number given the real and imaginary parts.

Modified: commons/proper/math/trunk/src/site/xdoc/changes.xml
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/site/xdoc/changes.xml?rev=729639&r1=729638&r2=729639&view=diff
==============================================================================
--- commons/proper/math/trunk/src/site/xdoc/changes.xml (original)
+++ commons/proper/math/trunk/src/site/xdoc/changes.xml Sat Dec 27 08:23:43 2008
@@ -39,6 +39,9 @@
   </properties>
   <body>
     <release version="2.0" date="TBD" description="TBD">
+      <action dev="luc" type="add" issue="MATH-236" due-to="Bernhard Grünewaldt">
+        Added nth root computation for complex numbers.
+      </action>
       <action dev="luc" type="add" issue="MATH-230" due-to="Sujit Pal and Ismael Juma">
         Added support for sparse matrix.
       </action>

Modified: commons/proper/math/trunk/src/test/org/apache/commons/math/complex/ComplexTest.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/test/org/apache/commons/math/complex/ComplexTest.java?rev=729639&r1=729638&r2=729639&view=diff
==============================================================================
--- commons/proper/math/trunk/src/test/org/apache/commons/math/complex/ComplexTest.java (original)
+++ commons/proper/math/trunk/src/test/org/apache/commons/math/complex/ComplexTest.java Sat
Dec 27 08:23:43 2008
@@ -695,5 +695,154 @@
     public void testMath221() {
         assertEquals(new Complex(0,-1), new Complex(0,1).multiply(new Complex(-1,0)));
     }
+    
+    /** 
+     * Test: computing <b>third roots</b> of z.
+     * <pre>
+     * <code>
+     * <b>z = -2 + 2 * i</b>
+     *   => z_0 =  1      +          i
+     *   => z_1 = -1.3660 + 0.3660 * i
+     *   => z_2 =  0.3660 - 1.3660 * i
+     * </code>
+     * </pre>
+     */
+    public void testNthRoot_normal_thirdRoot() {
+        // The complex number we want to compute all third-roots for.
+        Complex z = new Complex(-2,2);
+        // The List holding all third roots
+        Complex[] thirdRootsOfZ = z.nthRoot(3).toArray(new Complex[0]);
+        // Returned Collection must not be empty!
+        assertEquals(3, thirdRootsOfZ.length);
+        // test z_0
+        assertEquals(1.0,                  thirdRootsOfZ[0].getReal(),      1.0e-5); 
+        assertEquals(1.0,                  thirdRootsOfZ[0].getImaginary(), 1.0e-5);
+        // test z_1
+        assertEquals(-1.3660254037844386,  thirdRootsOfZ[1].getReal(),      1.0e-5);
+        assertEquals(0.36602540378443843,  thirdRootsOfZ[1].getImaginary(), 1.0e-5);
+        // test z_2
+        assertEquals(0.366025403784439,    thirdRootsOfZ[2].getReal(),      1.0e-5);
+        assertEquals(-1.3660254037844384,  thirdRootsOfZ[2].getImaginary(), 1.0e-5);
+    }
+
+
+    /** 
+     * Test: computing <b>fourth roots</b> of z.
+     * <pre>
+     * <code>
+     * <b>z = 5 - 2 * i</b>
+     *   => z_0 =  1.5164 - 0.1446 * i
+     *   => z_1 =  0.1446 + 1.5164 * i
+     *   => z_2 = -1.5164 + 0.1446 * i
+     *   => z_3 = -1.5164 - 0.1446 * i
+     * </code>
+     * </pre>
+     */
+    public void testNthRoot_normal_fourthRoot() {
+        // The complex number we want to compute all third-roots for.
+        Complex z = new Complex(5,-2);
+        // The List holding all fourth roots
+        Complex[] fourthRootsOfZ = z.nthRoot(4).toArray(new Complex[0]);
+        // Returned Collection must not be empty!
+        assertEquals(4, fourthRootsOfZ.length);
+        // test z_0
+        assertEquals(1.5164629308487783,     fourthRootsOfZ[0].getReal(),      1.0e-5); 
+        assertEquals(-0.14469266210702247,   fourthRootsOfZ[0].getImaginary(), 1.0e-5);
+        // test z_1
+        assertEquals(0.14469266210702256,    fourthRootsOfZ[1].getReal(),      1.0e-5);
+        assertEquals(1.5164629308487783,     fourthRootsOfZ[1].getImaginary(), 1.0e-5);
+        // test z_2
+        assertEquals(-1.5164629308487783,    fourthRootsOfZ[2].getReal(),      1.0e-5);
+        assertEquals(0.14469266210702267,    fourthRootsOfZ[2].getImaginary(), 1.0e-5);
+        // test z_3
+        assertEquals(-0.14469266210702275,   fourthRootsOfZ[3].getReal(),      1.0e-5);
+        assertEquals(-1.5164629308487783,    fourthRootsOfZ[3].getImaginary(), 1.0e-5);
+    }
+
+    /** 
+     * Test: computing <b>third roots</b> of z.
+     * <pre>
+     * <code>
+     * <b>z = 8</b>
+     *   => z_0 =  2
+     *   => z_1 = -1 + 1.73205 * i
+     *   => z_2 = -1 - 1.73205 * i
+     * </code>
+     * </pre>
+     */
+    public void testNthRoot_cornercase_thirdRoot_imaginaryPartEmpty() {
+        // The number 8 has three third roots. One we all already know is the number 2.
+        // But there are two more complex roots.
+        Complex z = new Complex(8,0);
+        // The List holding all third roots
+        Complex[] thirdRootsOfZ = z.nthRoot(3).toArray(new Complex[0]);
+        // Returned Collection must not be empty!
+        assertEquals(3, thirdRootsOfZ.length);
+        // test z_0
+        assertEquals(2.0,                thirdRootsOfZ[0].getReal(),      1.0e-5); 
+        assertEquals(0.0,                thirdRootsOfZ[0].getImaginary(), 1.0e-5);
+        // test z_1
+        assertEquals(-1.0,               thirdRootsOfZ[1].getReal(),      1.0e-5);
+        assertEquals(1.7320508075688774, thirdRootsOfZ[1].getImaginary(), 1.0e-5);
+        // test z_2
+        assertEquals(-1.0,               thirdRootsOfZ[2].getReal(),      1.0e-5);
+        assertEquals(-1.732050807568877, thirdRootsOfZ[2].getImaginary(), 1.0e-5);
+    }
+
+
+    /** 
+     * Test: computing <b>third roots</b> of z with real part 0.
+     * <pre>
+     * <code>
+     * <b>z = 2 * i</b>
+     *   => z_0 =  1.0911 + 0.6299 * i
+     *   => z_1 = -1.0911 + 0.6299 * i
+     *   => z_2 = -2.3144 - 1.2599 * i
+     * </code>
+     * </pre>
+     */
+    public void testNthRoot_cornercase_thirdRoot_realPartEmpty() {
+        // complex number with only imaginary part
+        Complex z = new Complex(0,2);
+        // The List holding all third roots
+        Complex[] thirdRootsOfZ = z.nthRoot(3).toArray(new Complex[0]);
+        // Returned Collection must not be empty!
+        assertEquals(3, thirdRootsOfZ.length);
+        // test z_0
+        assertEquals(1.0911236359717216,      thirdRootsOfZ[0].getReal(),      1.0e-5); 
+        assertEquals(0.6299605249474365,      thirdRootsOfZ[0].getImaginary(), 1.0e-5);
+        // test z_1
+        assertEquals(-1.0911236359717216,     thirdRootsOfZ[1].getReal(),      1.0e-5);
+        assertEquals(0.6299605249474365,      thirdRootsOfZ[1].getImaginary(), 1.0e-5);
+        // test z_2
+        assertEquals(-2.3144374213981936E-16, thirdRootsOfZ[2].getReal(),      1.0e-5);
+        assertEquals(-1.2599210498948732,     thirdRootsOfZ[2].getImaginary(), 1.0e-5);
+    }
+
+    /**
+     * Test cornercases with NaN and Infinity.
+     */
+    public void testNthRoot_cornercase_NAN_Inf() {
+        // third root of z = 1 + NaN * i
+        for (Complex c : oneNaN.nthRoot(3)) {
+            // both parts should be nan
+            assertEquals(nan, c.getReal());
+            assertEquals(nan, c.getImaginary());
+        }
+        // third root of z = inf + NaN * i
+        for (Complex c : infNaN.nthRoot(3)) {
+            // both parts should be nan
+            assertEquals(nan, c.getReal());
+            assertEquals(nan, c.getImaginary());
+        }
+        // third root of z = neginf + 1 * i
+        Complex[] zInfOne = negInfOne.nthRoot(2).toArray(new Complex[0]);
+        // first root
+        assertEquals(inf, zInfOne[0].getReal());
+        assertEquals(inf, zInfOne[0].getImaginary());
+        // second root
+        assertEquals(neginf, zInfOne[1].getReal());
+        assertEquals(neginf, zInfOne[1].getImaginary());
+    }
 
 }



Mime
View raw message