Jon Egeland
Jon Egeland

Reputation: 12613

Compute Logarithm

I'm trying to write a method that takes in a base k and a value n to 2 decimal places, then computes the log base k of n without using any of Java's Math.log methods. Here's what I have so far:

public static double log(double k, double n) {
    double value = 0.0;

    for(double i = 1; i > .001; i /= 10) {
        while(!(Math.pow(k, value) >= n )) {
            value += i;
        }
    }

    return value;
}

The problem comes up when I try computing log base 4 of 5.0625, which returns 2.0, but should return 1.5.

I have no idea why this isn't working. Any help is appreciated.

No this is not homework, it's part of a problem set that I'm trying to solve for fun.

Upvotes: 3

Views: 1697

Answers (5)

djdanlib
djdanlib

Reputation: 22486

Calculating logs by hand, what fun! I suggest doing it out on paper, then stepping through your code with watch variables or outputting each variable at each step. Then check this method out and see if it lines up with what you're doing: Link

Upvotes: 1

Meower68
Meower68

Reputation: 1009

You could always look at:

https://stackoverflow.com/a/2073928/251767

It provides an algorithm which will compute a log of any number in any base. It's a response to a question about calculating logs with BigDecimal types, but it could be adapted, pretty easily, to any floating-point type.

Since it uses squaring and dividing by two, instead of using multiple calls to Math.pow(), it should converge pretty quickly and use less CPU resources.

Upvotes: 0

Howard
Howard

Reputation: 39197

You're adding the amount i once too ofter. Thus you'll quite soon reach a value larger than the actual value and the while loop will never be entered again.

Subtract i once from the value and you'll be fine:

for(double i = 1; i > .001; i /= 10) {
    while(!(Math.pow(k, value) > n )) {
        value += i;
    }
    value -= i;
}

Upvotes: 5

Jason LeBrun
Jason LeBrun

Reputation: 13293

Step through the code on paper:

Iteration: i=1 value = 0.0, calculated power = 1
Iteration: i=1 value = 1.0, calculated power = 4
Iteration: i=1 value = 2.0, calculated power = 16

Now at this point, your value is 2.0. But at no point in the code to you have a way to correct back in the other direction. You need to check for both overshoot and undershoot cases.

Upvotes: 4

recursive
recursive

Reputation: 86084

This loop

    while(!(Math.pow(k, value) >= n )) {
        value += i;
    }

goes too far. It only stops after the correct value has been surpassed. So when calculating the ones place, 1 isn't enough, so it goes to 2.0, and all subsequent tests show that it is at least enough, so that's where it ends.

Upvotes: 1

Related Questions