C++ Square Root Function Bug

。_饼干妹妹 提交于 2020-01-15 04:51:09

问题


I have a c++ algorithm that calculates the square root of an integer. The program works with the exception of a single flaw. It is unable to calculate the square root of a number that is below 1. For example, it cant calculate the square root of .5 or .9 or .0000001 etc. but works as planned for all other situations. I have X set so it doesn't allow a negative input, but I still can't see why it wont return a value for anything less than 1.

include <iostream>
#include <cmath>
#include <cassert>

using namespace std;

double squareroot(double x)

{ /* computes the square root of x */

  /* make sure x is not negative .. no math crimes allowed! */
    assert(x >= 0);
    if (x == 0) return 0;

    /* the sqrt must be between xhi and xlo */
    double xhi = x;
    double xlo = 0;
    double guess = x / 2;

    /* We stop when guess*guess-x is very small */

    while (abs(guess*guess - x) > 0.000001)
    {
        if (guess*guess > x)  xhi = guess;
        else xlo = guess;
        guess = (xhi + xlo) / 2;
    }

    return guess;
}

/* Test Stub */


int main()
{
    double testvalue;
    cout << "\n Enter a TestValue= ";
    cin >> testvalue;
    cout << endl;
    double testresult = squareroot(testvalue);
    cout << "\n Square Root= " << testresult << "\n";
}

Thanks for the help! I was able to solve the problem by using the following:

if (x<1) {
    xhi = 1;
    xlo = x;
    guess = (x + 1) / 2;
}

回答1:


The square root of 0.5 is ~0.7. Your logic is guessing a smaller number if the check fails. What you need to do is add an extra detection layer to see if the number is < 1, and then modify the flow to increase the next guess instead of decreasing it.




回答2:


In case of x<1 you need change initial boundaries because square root locates not between 0 and x but between x and 1

double xhi, xlo, guess;
if (x > 1){
    xhi = x;
    xlo = 0;
    guess = x / 2;
}
else{
    xhi = 1;
    xlo = x;
    guess = (x + 1) / 2;
}



回答3:


Add some debugging output. That will help you understand why the program never converges to a solution when x < 1.0.

while (abs(guess*guess - x) > 0.000001)
{
    if (guess*guess > x)
    {
       cout << "Changing xhi\n";
       xhi = guess;
    }
    else
    {
       cout << "Changing xlo\n";
       xlo = guess;
    }

    guess = (xhi + xlo) / 2;
    cout << "guess: " << guess << endl;
}

If you follow the Newton-Raphson method, the program will converge faster. Also, it works regardless of whether x is greater than or less than 1.

double squareroot(double x)
{
   /* make sure x is not negative .. no math crimes allowed! */
   assert(x >= 0);
   if (x == 0) return 0;

   double guess = x / 2;
   while (abs(guess*guess - x) > 0.000001)
   {
      double dx = 0.5*(guess*guess -x)/guess;
      guess -= dx;
      cout << "guess: " << guess << endl;
   }

   return guess;
}


来源:https://stackoverflow.com/questions/34782086/c-square-root-function-bug

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!