Raffaele Rossi
Raffaele Rossi

Reputation: 3137

c++ continued fractions output error

I have written this Java code that works very well:

static String getFraction(double x) {
        double limit = 1.0E-6;     
        double h1 = 1, h2 = 0, k1 = 0, k2 = 1;
        double y = x;

        do {

            double a = Math.floor(y);
            double aux = h1;
            h1 = a*h1+h2;
            h2 = aux;
            aux = k1;
            k1 = a*k1+k2;
            k2 = aux;
            y = 1/(y-a);

        } while (Math.abs(x-h1/k1) > x*limit );

        return ((int) h1) + "/" + ((int) k1);  
    }

It takes a double (6.45) and returns its fractional representation using continued fractions (129/20). This is the C++ code:

 void calc(double x) {

    double limit = 1.0E-6;     
    double h1 = 1, h2 = 0, k1 = 0, k2 = 1;
    double y = x;

    do {

        double a = floor(y);
        double aux = h1;
        h1 = a*h1+h2;
        h2 = aux;
        aux = k1;
        k1 = a*k1+k2;
        k2 = aux;
        y = 1/(y-a);

    } while (abs(x-h1/k1) > x*limit );

    std::cout << (h1) << "/" << (k1) << std::endl;  
 }

The C++ translation is in my opinion identical to the Java version. The problem is this output:

Java (input 6.45) --> 129/20
C++ (input 6.45) --> 6/1

Any idea? Do I have to static cast something to double to allow floating point operations?

Upvotes: 0

Views: 137

Answers (2)

David
David

Reputation: 1520

The abs function returns an int which will be 0. You want to either use fabs or std::abs, the latter has overloads for both integral and floating point types.

Upvotes: 2

Alberto Miola
Alberto Miola

Reputation: 4751

The problem is the abs() function. I have had a similar problem in the past. Look at this code:

int main() {
  std::cout << abs(-85.5) << std::endl;
}

The output is 85. You have two solutions:

  1. use fabs()
  2. do a workaroud:

Something like this

double c;

do {

  double a = floor(y);
  double aux = h1;
  h1 = a*h1+h2;
  h2 = aux;
  aux = k1;
  k1 = a*k1+k2;
  k2 = aux;
  y = 1/(y-a);

  if ((x-h1/k1) >= 0)
    c = x-h1/k1; 
  else
    c = -(x-h1/k1);

} while (c > x*limit );

Upvotes: 1

Related Questions