Fibonacci sequence problem

 The solution to the Fibonacci sequence:

 1. Recursive algorithm

 The concept of recursion , I do not understand, the language is not good. But the core idea, I think, is to push and pop the stack. For example, if you want to ask for a certain result, if you can't solve it in one step, then push the calculation step of the last step into the stack first, without considering it. Turn to think about how to do the step before the last step, just like wearing clothes in winter, and before the last step wearing a down jacket, I think most people will wear a sweater (if it is more serious, underwear you should will wear it). In this way, we first put the down jacket aside (into the stack) and go to prepare to wear the wool sweater. Then we found out that I had to wear thermal underwear before wearing the cardigan. OK, let's put the sweater aside first (and then push it into the stack, at this time the sweater is placed on top of the down jacket). At this time, we put on thermal underwear, ok one -> the last-in-first-out rule of the stack indicates that the next I should wear a wool sweater, ok put on the next one -> down jacket. . . (The dressing process for the lower body is similar, there may be one more fat time, and you can make up your own mind).

 So you see, in reality, many times things are not done at once, but need to be done step by step, especially the program. The purpose of the code you design is to solve a problem. In the process of solving, there will be many steps. The same is true for recursion, but it keeps calling itself before solving the problem.

   Take a look at this Fibonacci sequence:

  The recursive formula of the Fibonacci sequence is: Fn=Fn-1+Fn-2, where F1=F2=1.

  When n is relatively large, Fn is also very large, and now we want to know, what is the remainder of dividing Fn by 10007.

  The first step, what is n. Enter n according to the meaning of the title.

  The second step, how to ask, here I assume there is such a method called Fibonacci (int n), return an int, after passing n in, after this method, I get Fn.

  The third step, analyze, Fn=Fn-1+Fn-2=Fn-2+Fn-3+Fn-3+Fn-4=......... So, request Fn (down jacket) , first go to find Fn-1 and Fn-2 (wool sweater), if you require Fn-1, you must first find Fn-2 and Fn-3, and so on, if you can't find it temporarily, all of them are put into the stack in turn, and finally It is found that F3 is required, and I have to first seek F2 and F1 (F3 is pushed onto the stack). OK, F1=F2=1, F3 is obtained (F3 is popped out of the stack), and F4=F3+F2, F4 is also obtained (F4 is out of the stack)....... Those steps before the stack , and then pop the stack to calculate until Fn is obtained, and the calculation of Fn%10007 is over.

  The fourth step, put the code:

import java.util.Scanner;

public class Fibonacci {
	//Fibonacci sequence recursive algorithm
	public static int Fibonacci (int n){
		if(n==1||n==2){
			return 1;
		} else{
                        //Operate the core of stacking and popping, recursive call
			n = Fibonacci (n-1) + Fibonacci (n-2);
			return n;
		}
	}

	public static void main(String[] args) {
		while(true){
			Scanner scanner = new Scanner(System.in);
			int n;
			n = scanner. nextInt();
			int k = Fibonacci (n);
			System.out.println(k%10007);	
		}

	}

}        

  

 2. Integer remainder

    Although the code of the recursive algorithm is concise, it has a disadvantage, that is, the execution efficiency is very low. It is a deep call by itself, and the complexity in time and space is very high, and the calculation is repetitive. There are many operations, and it is very likely to cause stack overflow in the computer. For example, when recursively calculating the Nth order, when the value of N becomes larger and larger, it is very likely that the computer will fail.

    Therefore, based on the same principle of recursion and loop theory, combined with the rule of integer remainder, the code is improved as follows:

import java.util.Scanner;

public class Fibonacci {
	//Fibonacci sequence remainder algorithm
	public static int Fibonacci(int n){
		int[] F = new int[n+1];//n+1 is to prevent the array from going out of bounds
		F[1]=F[2]=1;
		for(int i=3;i<=n;i++){
			F[i] = (F[i-1] + F[i-2])%10007;
		}
		return F[n];
	}
	public static void main(String[] args) {
		while(true){
			Scanner scanner = new Scanner(System.in);
			int n;
			n = scanner. nextInt();
			System.out.println(Fibonacci(n));
			
		}

	}

}

    In the method, define an int array with a length of n+1 to store the value of the sequence, where n+1 is to prevent the array from going out of bounds during the execution process. Then, the core of the method lies in the calculation of integer remainder, namely:

F[i] = (F[i-1] + F[i-2])%10007;

Why is it written like this? When the code is improved like this, we don't need to find the value of Fn first and then take the remainder, but directly in the for loop, we can directly execute the remainder operation, when the loop ends. The final Fn is the result of taking the remainder of the Nth number in the sequence.
Why can it be written like this? There is a rule for integer remainder operation. For example, 1%10 is 1, 2%10 is 2, and 3%10 is 3. Is that 3%10=1%10+2%10? ? Here are a few more examples to verify:

5%10=5; 10%10=0; 15%10=5=5%10+10%10;
21%10=1; 32%10=2; 53%10=3=21%10+32% 10;
57%7=1; 89%7=5; 146%7=6=57%7+89%7;
......
You can see that it seems to be the case. The principle is that you It is understandable to think about it, but I am not very clear about it. I am afraid of mistaking others. If you want to understand more deeply, you can Baidu.
Attached a link to the blog of a senior I found and recorded the remainder calculation rules: https://blog.csdn.net/ash_zheng/article/details/38541777
I will write this for the time being, welcome to comment and exchange, learn from each other, haha .

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=325327403&siteId=291194637