Calculate the power of 2, java - java

I want to calculate the power of 2 using recursion. Here is my code:
class Aufg1{
public static void main(String args[]){
int erg = zweiHochPositiv(10);
}
public static int zweiHochPositiv(int exponent){
if(exponent > 0)
return (2*zweiHochPositiv(exponent--));
else
return 1;
}
}
I get a lot of errors at
return (2*zweiHochPositiv(exponent--));
but I have no idea what may be wrong.

Replace
return (2*zweiHochPositiv(exponent--));
with
return (2*zweiHochPositiv(exponent - 1));
exponent-- evaluates to the value of the exponent variable and then decrements it. So when you call zweiHochPositiv(1), the method will call zweiHochPositiv(1) again.
As a result, this method, when called with a value > 0, will recurse indefinitely and ultimately overflow the stack.

You need to use prefix version of --.
This should work:
return (2*zweiHochPositiv(--exponent));
Explanation: exponent-- will never actually lower exponent's value, so you're calling your recursive function every time with the same value, and that will blow your stack.
--exponent will lower it's value by one, so you should get desired behaviour.

I think an efficient way of doing it would be to use the binary representation property of a "power of 2" - its just a bit shift of 1, "exponent" number of times.
Hence, 2^2 = 1 << 2 = (in binary) ....0000 0100 = 4

return (2*zweiHochPositiv(--exponent));

Related

Recursion gives unexpected/wrong output?

So I was doing a recursion challenge on codingbat and came across the "bunny ears" problem where we have a number of bunnies and each bunny has two big floppy ears. We want to compute the total number of ears across all the bunnies recursively (without loops or multiplication).
The solution apparently is quite simple:
public int bunnyEars(int bunnies)
{
if(bunnies == 0)
return 0;
return 2+bunnyEars(bunnies-1);
}
But I am not able to understand. If we pass 2 in the bunnyEars(2) method the
recursive part bunnyEars(bunnies-1); should have 1 left in the bracket after subtraction and thus 2+(1); which should be equal to 3 and not 4.
But the output comes as 4. So how does recursion actually work in this code?
It is not 2+(1), it is 2+numberOfEarsOfBunnies(1) == 2+2.
I renamed the function a little to make it more obvious.
Or even more into detail:
numberOfEarsOfBunnies(2)==
2+numberOfEarsOfBunnies(1)==
2+(2+numberOfEarsOfBunnies(0))==
2+(2+0)==
2+2==
4
if we pass 2 in the bunnyEars(2) method the recursive part bunnyEars(bunnies-1); should have 1 left in the bracket after subtraction and thus 2+(1); should be equal to 3 and not 4.
It seems you're misreading the expression. The line of code in question says
return 2+bunnyEars(bunnies-1);
Now you call bunnyEars(2), so bunnies == 2; and then you reach this line of code.
return 2+bunnyEars(bunnies-1);
resolves to
return 2+bunnyEars(2-1);
or
return 2+bunnyEars(1);
So a second instance of the bunnyEars() function starts running, with bunnies == 1. It reaches that same line of code, and this time
return 2+bunnyEars(bunnies-1);
is
return 2+bunnyEars(1-1);
or
return 2+bunnyEars(0);
So a third instance of bunnyEars() gets running, with bunnies == 0; but this matches your base case, so you just return 0 ; this time we don't recurse. So back up a level we find that
return 2+bunnyEars(0);
is
return 2+0; // because bunnyEars(0) returned 0
so that instance returns 2. And that means
return 2+bunnyEars(1);
becomes
return 2+2; // because bunnyEars(1) returned 2
And of course 2+2 is 4, the correct answer.
It seems as though you applied the -1 to the return value of the recursive bunnyEars() call, but the code says to apply it to the parameter you're sending in, not to the return value.

Recursion confusion with multiple return

I'm still wrapping my mind around recursion, and I think I get basic ones like factorial. But I'd like further clarification when the return statement is a little more complex like on the following snippet:
/**
* #param n >= 0
* #return the nth Fibonacci number
*/
public static int fibonacci(int n) {
if (n == 0 || n == 1) {
return 1; // base cases
} else {
return fibonacci(n-1) + fibonacci(n-2); // recursive step
}
}
In the return statement, does the fibonacci(n-1) completely recur through, before going down the fibonacci(n-2) step (does that make sense)? If so, this seems very difficult to envision.
Yes, one invocation will recurse all the way down and return, before the other one starts executing.
The order of invocation in Java is well-defined: fibonacci(n-1) goes before fibonacci(n-2).
Edit: Since the question originally included [C++] tag, here is the C++ part of the story: one of the two invocations still has to complete before the other one starts to run, but which one, fibonacci(n-1) or fibonacci(n-2), is unspecified.
Since the function has no side effects, it does not matter which of the two invocations gets to run first. The only thing that is important for understanding of recursion is that both invocations must complete, and their results must be added together, before the invocation at the current level returns.
It isn't much more different than calling a different function than itself. It needs to finish before the calling function can do anything with the result.
finobacci(0); // ==> 1 (since n is zero, the base case is to return 1)
fibonacci(1); // ==> 1 (since n is one, the base case is to return 1)
Now lets try 2 which is not the base case:
fibonacci(2); // == (since it's not the base case)
fibonacci(1) + fibonacci(0); // == (both calls to fibonacci we already haver done above)
1 + 1 // ==> 2
So in reality what happens is that the call to fibonacci2 waits while each of the two recursive calls to finish, just like a function that does System.out.println would wait until it had printed the argument before continuing to the next line. Recursion isn't that special.
Trivia: This is the original series from Fibonacci himself. Modern mathematicians start the series with n as the base case result making the series 0, 1, 1, 2, ... rather than 1, 1, 2, 3, ....
it works in this way:
Fibonacci program:
public int fibonacci(int n) {
if(n == 0)
return 0;
else if(n == 1)
return 1;
else
return fibonacci(n - 1) + fibonacci(n - 2);
}
Explanation:
In fibonacci sequence each item is the sum of the previous two. So, as per recursive algorithm.
So,
fibonacci(5) = fibonacci(4) + fibonacci(3)
fibonacci(3) = fibonacci(2) + fibonacci(1)
fibonacci(4) = fibonacci(3) + fibonacci(2)
fibonacci(2) = fibonacci(1) + fibonacci(0)
Now you already know fibonacci(1)==1 and fibonacci(0) == 0. So, you can subsequently calculate the other values.
Now,
fibonacci(2) = 1+0 = 1
fibonacci(3) = 1+1 = 2
fibonacci(4) = 2+1 = 3
fibonacci(5) = 3+2 = 5
In multiple recursion the program calls itself with its first call until the base case is reached, in this case fibonacci(n-1); after that the recursion stops and return his value to continue calling the value to the second part of the recursion fibonacci(n-2).
If you don't visualize the multiple recursion in the program, this
fibonacci recursion tree may be helpful.

How to correct my java recursive method so that I can use it to compute big value number?

It started from I want to compute 1+2+3+...+n, and
It is easy for me to figure out an recursive method to deal with repeat-plus-operation, and the code as follow:
public long toAccumulate(long num)
{
return num == 1 ? 1 : num + toAccumulate(num-1);
}
This method works just fine when use in a range of small number like 1 to 100, however, it fails to work when the parameter up to a big number like 1000000.
I wonder why?
And one leads to another, I write a repeat-times-operation method as follow:
public long toTimes(long num)
{
return num == 1 ? 1 : num * toTimes(num-1);
}
And here comes some interesting result. If I pass 100 as parameter, I will get 0. So I decrease my parameter's value, and I finally got some number when the parameter passing 60, but the result was a very weird negative number -8718968878589280256.
This got me thinking, but it didn't too much time for me to rethink something I have learnt from C, which is long long big data value type. And I assumed that negative number showed off is because the result data too big to fit in the current data type. What amazed me was I realize that there's a BigInteger class in Java, and I remembered this class can operate the big value data, so I changed the first code as follow:
public BigInteger toAccumulate(BigInteger num)
{
return num.equals(1) ? BigInteger.valueOf(1) : (num.add(toAccumulate(num.subtract(BigInteger.valueOf(1)))));
}
But it still didn't work... and this is driving me crazy...
A question I found in the stack overflow which similar to mine
According to the people who answered the question, I guess it may be the same reason that cause the bug in my code.
But since the BigInteger class didn't work, I think this must be the solution to this kind of accumulation problem.
What will you people do when you need to accumulate some number and prevent it go out of the maximum of data type? But is this really the data type problem?
return num.equals(1)
? BigInteger.valueOf(1)
: (num.add(toAccumulate(num.subtract(BigInteger.valueOf(1)))));
should probably be
return num.equals(BigInteger.valueOf(1))
? BigInteger.valueOf(1)
: (num.add(toAccumulate(num.subtract(BigInteger.valueOf(1)))));
...though frankly I'd write it as a method accepting an int and returning a BigInteger.
What if you try this:
public static BigInteger toAccumulate (BigInteger num)
{
if (num.equals(BigInteger.valueOf(1)))
{
return BigInteger.valueOf(1) ;
}
else
{
// 1+2+...+(n-1)+n = (n)(n+1)/2
BigInteger addOne = num.add(BigInteger.valueOf(1));
return num.multiply(addOne).divide(BigInteger.valueOf(2));
}
}
Here's how you can do the 1*2*3*....*(n-1)*n
public static BigInteger toTimes (BigInteger num)
{
// Should check for negative input here
BigInteger product = num;
// while num is greater than 1
while (num.compareTo(BigInteger.valueOf(1)) == 1)
{
BigInteger minusOne = num.subtract(BigInteger.valueOf(1));
product = product.multiply(minusOne);
num = minusOne; // num--;
}
return product;
}
Note: This is essentially the Factorial Function

Return inside of recursive function doesn't 'work' if short if is used

I have this odd issue I can't explain to myself, when using short if inside of return. This code (see below) should return the value 55 but instead it just returns the argument 10 which I passed to it by value.
I already debugged the function and the recursion works as intended but it never adds the + 1 to the return value.
public static int add(int i) {
return i == 0 ? 0 : add(i - 1) + 1;
}
public static void main(String[] args) {
System.out.println(add(10)); // returns 10
}
How come this doesn't work?
Your code does what you're telling it to. At each recursion step it reduces one from the counter and adds 1 to the result - since it's counting i times, it'll return i.
What you're trying to do is sum the numbers from 0 to i. In order to do this you need to add i and not 1 to the sum each time.
public static int add(int i) {
return i == 0 ? 0 : add(i - 1) + i; // <- like this
}
Since this is likely an exercise, consider implementing factorial recursively to make sure you understand the concept (that is, a function that takes n and returns n * (n-1) * (n-2) ... and so on.

Java Recursion - Did I do this right? [closed]

Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 8 years ago.
Improve this question
My job is to write a recursive version to this method. From what I understand Recursion is starting with a base call (if something then return) followed by an else which unwinds back to the original base. Like starting with a deck, adding on to the deck then removing cards from the deck until you are back to the original deck.
With that in mind here it is.
public static long fact(int n)
{
long result = 1;
while(n > 0)
{
result = result * n;
n = n - 1;
}
return result;
}
//my recursive version:
public static void recFact(int n)
{
if(n==0)
{
return n; // ir 0 it really doesn't matter right?
}
else
{
return recFact(n-1);
}
}
This is just an example test problem for an exam I have coming up, just want to make sure I have a handle on recursion. Did I do this right? If not what am I missing? please no answers in questions, just tell me what I did wrong and maybe some advice on better ways to understand it.
Thanks.
No, this recursive solution is not correct.
For every positive n, you're just return rectFact(n-1), which will recourse until you reach 0, at which point it will return. In other words, your function will always return 0. You're missing the part where you multiply the current n with rectFact(n-1). Additionally, note that 0! is 1, not 0:
public static int recFact(int n)
{
if(n==0)
{
return 1;
}
else
{
return n * recFact(n-1);
}
}
And finally, since the if clause returns, the else is somewhat redundant. This doesn't affect the method's correctness, of course, but IMHO the code looks cleaner without it:
public static int recFact(int n)
{
if(n==0)
{
return 1;
}
return n * recFact(n-1);
}
Your recursive version does no multiplication, and it will return zero for any input. So no, you didn't do it right.
But, the recursive version DOES recurse, so you have that going for you! To understand what's going wrong, walk through a very simple case.
Client calls recFact(3)
This will return to client recFact(2)
Which will return to above recFact(1)
Which will return to above recFact(0)
Which will return to above 0.
There are two major things going wrong:
Your base case is wrong (zero is too low)
You're not doing any multiplication
Good attitude about not wanting the solution handed to you! Hopefully these pointers wil help you figure it out.
EDIT: Apparently I misunderstood your grammar and you did want the solution.
Any recursive function needs three things:
The terminating condition: This tells the function when to stop calling itself. This is very important to avoid infinite recursion and avoid stack overflow exceptions.
The actual processing: You need to run the actual processing within each function. In your non recursive case, this was result = result * n. This is missing from your recursive version!
A collector/agggregator variable: You need some way to store the partial result of the recursive calls below you. So you need some way to return the result of recFact so that you can include it in processing higher up in the call chain. Note that you say return recFact(n - 1) but in the definition recFact returns void. That should probably be an int.
Based from your example you are missing the return type of your recFact which is int
Also recFact will always return 0 because you are not multiplying n each time to the recursion call of the method.
There are two ways to write recursive routines. One is the "standard" way that we all are taught. This is one entry point that must first check to see if the recursive chain is at an end (the escape clause). If so, it returns the "end of chain" value and ends the recursion. If not at the end, it performs whatever calculation it needs to get a partial value according to the level and then calls itself passing a value the next increment closer to the end of the chain.
private final int InitialValue = 15;
System.out.println( "Fact(" + InitialValue + ") = " + recFact( InitialValue ) );
public int recFact( int val ){
if( val < 2 ){
return 1;
}
else{
return recFact( val - 1 ) * val; // recursive call
}
}
//Output: "Fact(15) = 2004310016"
In regular recursion, a partial answer is maintained at each level which is used to supplement the answer from the next level. In the code above, the partial answer is val. When first called, this value is 15. It takes this value and multiplies it by the answer from Fact(14) to supply the complete answer to Fact(15). Fact(14) got its answer by multiplying 14 by the answer it got from Fact(13) and so on.
There is another type of recursion called tail recursion. This differs in that partial answers are passed to the next level instead of maintained at each level. This sounds complicated but in actuality, make the recursion process much simpler. Another difference is that there are two routines, one is non recursive and sets up the recursive routine. This is to maintain the standard API to users who only want to see (and should only have to see)
answer = routine( parameter );
The non-recursive routines provides this. It is also a convenient place to put one-time code such as error checking. Notice in the standard routine above, if the user passed in -15 instead of 15, the routine could bomb out. That means that in production code, such a test must be made. But this test will be performed every time the routine is entered which means the test will be made needlessly for all but the very first time. Also, as this must return an integer value, it cannot handle an initial value greater than 19 as that will result in a value that will overflow the 32-bit integer container.
public static final int MaxFactorialSeq = 20;
private final int InitialValue = 15;
System.out.println( "Fact(" + InitialValue + ") = " + recFact( InitialValue ) );
public int recFact( int value ){
if( value < 0 || value > MaxFactorialSeq ){
throw new IllegalArgumentException(
"Factorial sequence value " + value + " is out of range." );
}
return recFact( value, 1 ); // initial invocation
}
private int recFact( int val, int acc ){
if( val < 2 ){
return acc;
}
else{
return recFact( val - 1, acc * val ); // recursive call
}
}
//Output: "Fact(15) = 2004310016"
Notice the public entry point contains range checking code. This is executed only once and the recursive routine does not have to make this check. It then calls the recursive version with an initial "seed" of 1.
The recursive routine, as before, checks to see if it is at the end of the chain. If so, it returns, not 1 as before, but the accumulator which at this point has the complete answer. The call chain then just rewinds back to the initial entry point in the non-recursive routine. There are no further calculations to be made as the answer is calculated on the way down rather than on the way up.
If you walk though it, the answer with standard recursion was reached by the sequence 15*14*13*...*2*1. With tail recursion, the answer was reached by the sequence 1*15*14*...*3*2. The final answer is, of course, the same. However, in my test with an initial value of 15, the standard recursion method took an average of 0.044 msecs and the tail recursion method took an average of 0.030 msecs. However, almost all that time difference is accounted for by the fact that I have the bounds checking in my standard recursion routine. Without it, the timing is much closer (0.036 to 0.030) but, of course, then you don't have error checking.
Not all recursive routines can use tail recursion. But then, not all recursive routines should be. It is a truism that any recursive function can be written using a loop. And generally should be. But a Factorial function like the ones above can never exceed 19 levels so they can be added to the lucky few.
The problem with recursion is that to understand recursion you must first understand recursion.
A recursive function is a function which calls itself, or calls a function which ultimately calls the first function again.
You have the recursion part right, since your function calls itself, and you have an "escape" clause so you don't get infinite recursion (a reason for the function not to call itself).
What you are lacking from your example though is the actual operation you are performing.
Also, instead of passing a counter, you need to pass your counter and the value you are multiplying, and then you need to return said multiplied value.
public static long recFact(int n, long val)
{
if(n==1)
{
return val;
}
else
{
return recFact(n-1, val) * n;
}
}

Categories

Resources