Finding the cubic root

I couldn't find any function for the cubic root in the System.Math class, only the Math.Sqrt() function, I decided to write my own function. After some searching I found out about the formula for Newton approximation method and implemented it in my own function. As you might understand, you can only approximate it.
If you are in need of computing the cubic root, please feel free to copy and paste the code, or change it if you want. I see no reason to protect this code that isn't even optimized yet. If you anyone has any suggestions how to improve it, please post it here.

/// <summary>
/// Computes an approximate cube root of a number,
/// by using the Newton approximation for next guess.
/// </summary>
/// <param name="x">The number to compute the cube root from.</param>
/// <returns></returns>
public static double Cbrt(double x)
{
double y; // Guess
double d; // Last difference of y3 and x
double l; // The limit for optimal guess

// Check for simple cases:
#region
if (x == 0)
return 0;
else if (x == 1)
return 1;
else if (x == -1)
return -1;
else
#endregion
{

l = Math.Abs(x * 1E-14); // Set the limit appropriately
// the multiplication with x (its magnitude) should
// ensure no infinite loops, at the cost
// of some precision on high numbers.

// Make initial guess:
#region
double g = Math.Abs(x); // Do this guess on a positive number
if (g < 1)
y = x;
else if (g < 10)
y = x / 3;
else if (g < 20)
y = x / 6;
else if (g < 50)
y = x / 10;
else if (g < 100)
y = x / 20;
else if (g < 1000)
y = x / 50;
else if (g < 5000)
y = x / 100;
else if (g < 10000)
y = x / 500;
else if (g < 50000)
y = x / 1000;
else if (g < 100000)
y = x / 50000;
else
y = x / 100000;
#endregion

// Improve guess immediately:
y = ((x / (y * y)) + 2 * y) / 3; // Newton's approx. for new guess
d = Math.Abs(y * y * y - x); // Calculate difference
#region
while (l < d)
{
y = ((x / (y * y)) + 2 * y) / 3; // Newton's approx. for new guess
d = Math.Abs(y * y * y - x); // Calculate difference
}
#endregion
return y;
}
}

The biggest flaw of code would probably be the initial guess. Another way to do it would just be to find x^(1/3), but you never know what initial guesses happens inside either. The initial guess branching can't be too big, as bigger numbers will make the function take longer time because of more testing, and it can't be too small as bigger numbers will require more improvements.
I wrote a profiled version of the function, and found the following averages:
Number of improvements: Ranging from 5~8 for smaller numbers, to over a hundred
Time spent: 5000 ticks over 3.5million ticks (using System.Diagnostics.Stopwatch) on first run (because of JIT), which dropped down to ~150 on all following trials.


Answer this question

Finding the cubic root

  • Sekhmet

    At least it shows how cubic roots may be found other than using fractional powers. I doubt many of you can work out an algorithm to calculate a number to the power of any non-integer number.

  • ashish taralekar

    you have it. . . x^(1/3). . . how would you calculate x^5

    hmmmmm



  • Rturlapati

    Hope this helps

    private double CubicRoot(double x)
    {
    return Math.Pow(x, (1.0 / 3.0));
    }



  • Finding the cubic root