zoukankan      html  css  js  c++  java
  • Java实现斐波那契数列的多种方法

    小编综合了很多算法相关的书籍以及其他,总结了几种求斐波那契数列的方法

    PS:其中的第83行的递归法是求斐波那契数列的经典方法

    
    public class 斐波那契数列 {
    	
    	  //迭代法
        public static int iteration(int n){   /*此处(包含下面所有方法)声明为静态方法,原因是在本类main()方法中调用
            类中方法,对于一般的非static成员变量或方法,需要有一个对象的实例才能调用,所以要先生成对象的实例,他们才会实际的分配内存空间。
            而对于static的对象或方法,在程序载入时便已经分配了内存空间,他只和特定的类想关联,无需实例化  */
            int result = 1;  //最后一个斐波那契数
            int a[] = new int[n+1];    //存放斐波那契数,初始值为空,默认全为0
            a[0] = 0;
            a[1] = 1;
            //System.out.println("迭代法计算斐波那契数结果:");
            //System.out.print(a[0]+"  "+a[1]+"  ");
            for(int i = 2;i < n+1;i++){
                a[i] = a[i-1] + a[i-2];
                //result = a[i];
                //System.out.print(result+"  ");        //打印斐波那契数
            }
            //System.out.println();
            result=a[n];
            return result;    //返回最后一个斐波那契数
        }
        
        //用迭代法寻找编程环境支持的最大整数(int型)的斐波那契数是第几个斐波那契数
        public static int max_int_iteration(){
            int a = 1,b = 1,c = 2;
            int count = 3;
            for( ;b < c; ){   //一旦c达到编程环境最大斐波那契数,便会产生内存溢出,从而变成一个负数,到此循环结束
                a = b;
                b = c;
                c = a + b;
                count++;
            }
            return count;
        }
        
        
        //用迭代法寻找编程环境支持的最大整数(long型)的斐波那契数是第几个斐波那契数
        public static long max_long_iteration(){
            long a = 1,b = 1,c = 2;
            long count = 3;
            for( ;b<c; ){    //一旦c达到编程环境最大斐波那契数,便会产生内存溢出,从而变成一个负数,到此循环结束
                a = b;
                b = c;
                c = a + b;
                count++;
            }
            return count;
        }
        
        //在1,5,10,50秒内使用迭代法算出的最大斐波那契数是第几个
            public static void time_iteration(){
                int a = 1,b = 1,c = 2;
                long count = 3;
                long a1 = 0,a2 = 0,a3 = 0,a4 = 0;
                long t1 = System.currentTimeMillis(); 
                long t2 = System.currentTimeMillis();
                for( ;t2-t1 < 60000; ){   
                    a = b;
                    b = c;
                    c = a + b;
                    count++;
                    t2 = System.currentTimeMillis(); 
                    if(t2-t1 == 1000)
                        a1 = count;
                        //System.out.println("1秒内最大斐波那契数是第:"+count+"个 ");
                    if(t2-t1 == 5000)
                        a2 = count;
                        //System.out.println("5秒内最大斐波那契数是第:"+count+"个 ");
                    if(t2-t1 == 10000)
                        a3 = count;
                        //System.out.println("10秒内最大斐波那契数是第:"+count+"个 ");
                    if(t2-t1 == 50000)
                        a4 = count;
                        //System.out.println("50秒内最大斐波那契数是第:"+count+"个 ");
                }
                System.out.println("迭代法1秒内最大斐波那契数是第:"+a1+"个 ");
                System.out.println("迭代法5秒内最大斐波那契数是第:"+a2+"个 ");
                System.out.println("迭代法10秒内最大斐波那契数是第:"+a3+"个 ");
                System.out.println("迭代法50秒内最大斐波那契数是第:"+a4+"个 ");
            }
        
        //递归法
        public static long recursion(long n){
            long result = 0;   //最后一个斐波那契数及存储中间斐波那契数的变量
            if(n <= 0)
                result = 0;
            if(n == 1 || n == 2)
                result = 1;
            if(n > 2)
            {
                result = recursion(n-1) + recursion(n-2);
                //System.out.print(result+"  ");
            }
            return result;
        }
        
        //规定时间内,递归法计算出的最大斐波那契数是第几个
        public static int recursion_time(long time){
            long starttime_dg=System.currentTimeMillis();
            int i=3;
            long endtime_dg=0;
            while(endtime_dg<starttime_dg+time*1000){
            endtime_dg=System.currentTimeMillis();
            i++;
            recursion(i);
            }
            return i;
            }
        
        //递归法在1,5,10,50秒内算出的最大斐波那契数是第几个
        public static void fbnq_recursion_time(){
            
                  System.out.println("1秒内最大斐波那契数是第:"+recursion_time(1)+"个 ");
              
                  System.out.println("5秒内最大斐波那契数是第:"+recursion_time(5)+"个 ");
              
                  System.out.println("10秒内最大斐波那契数是第:"+recursion_time(10)+"个 ");
              
                  System.out.println("50秒内最大斐波那契数是第:"+recursion_time(50)+"个 ");
            
            
            }
        
        //测试递归法在1,5,10,50秒内使用迭代法算出的最大斐波那契数是第几个
        public static void time_recursion_test(){
            long t1 = System.currentTimeMillis(); 
            long t2 = 0;
            int i = 3;        
            for(;t2-t1 > 60000;){
                recursion(i);
                i++;
                t2 = System.currentTimeMillis();
                if(t2-t1 == 1000)
                    System.out.println("1秒内最大斐波那契数是第:"+i+"个 ");
                if(t2-t1 == 5000)
                    System.out.println("5秒内最大斐波那契数是第:"+i+"个 ");
                if(t2-t1 == 10000)
                    System.out.println("10秒内最大斐波那契数是第:"+i+"个 ");
                  if(t2-t1 == 50000)
                    System.out.println("50秒内最大斐波那契数是第:"+i+"个 ");
                
            }
        }
        
        //直接求值法(利用公式F(n) = [@n/sqrt(5)]快速计算第n个斐波那契数)
        public static double formula(int n){
            double result = 0;
            double temp = Math.sqrt(5.0);
            result =  (1/temp)*(Math.pow((1+temp)/2,n)-Math.pow((1-temp)/2, n));
            return result;
        }
        
        
        //利用直接求值法,出现误差时最小的n值
        public static int min_formula(){
            double result_fn=1;
            int i=1;
            while(result_fn-(double)iteration(i)<1){
            result_fn=formula(i);
            i++;
            }
            return i;
        }
        
        //新算法法
        public static int new_way(int n){
            //int a = 1,b = 1,c = 2,d = 3;
            int result = 0;   //定义最后一个斐波那契数
            //根据输入n,求出最后一个斐波那契数
            if(n == 0)
                result = 0;
            else if(n == 1 || n == 2)
                result =  1;
            else if(n == 3)
                result =  2;
            else if(n >= 4){    //若n大于4返回resul
                int a1 = n/4;
                int b1 = n%4;
                int a = new_way(a1);
                int b = new_way((a1+1));
                int c = new_way((a1-1));
                int d = new_way((a1+2));
                if(b1 == 0)
                    result = (int) ((Math.pow(b,2) - Math.pow(c,2))*(Math.pow(c, 2) + 2*Math.pow(a, 2) + Math.pow(b,2)));
                if(b1 == 1)
                    result = (int) (Math.pow((Math.pow(b,2) - Math.pow(c,2)),2) + Math.pow((Math.pow(a, 2) + Math.pow(b,2)),2));
                if(b1 == 2)
                    result = (int) ((Math.pow(a, 2) + Math.pow(b,2))*(3*Math.pow(b,2)+Math.pow(a, 2)-2*Math.pow(c,2)));
                if(b1 == 3)
                    result = (int) (Math.pow((Math.pow(a, 2) + Math.pow(b,2)),2) + Math.pow((Math.pow(d,2)-Math.pow(a,2)),2));
            
            }
                return result;
        }
        
        
        // 关联矩阵  
        private static final int[][] UNIT = { { 1, 1 }, { 1, 0 } };  
        // 全0矩阵  
        private static final int[][] ZERO = { { 0, 0 }, { 0, 0 } };  
        /** 
         * 求斐波那契数列 
         *  
         * @param n 
         * @return 
         */  
        public static int[][] fb(int n) {  
            if (n == 0) {  
                return ZERO;  
            }  
            if (n == 1) {  
                return UNIT;  
            }  
            // n是奇数  
            if ((n & 1) == 0) {  
                int[][] matrix = fb(n >> 1);  
                return matrixMultiply(matrix, matrix);  
            }  
            // n是偶数  
            int[][] matrix = fb((n - 1) >> 1);  
            return matrixMultiply(matrixMultiply(matrix, matrix), UNIT);  
        }  
          
        /** 
         * 矩阵相乘 
         *  
         * @param m 
         *            r1*c1 
         * @param n 
         *            c1*c2 
         * @return 新矩阵,r1*c2 
         */  
        public static int[][] matrixMultiply(int[][] m, int[][] n) {  
            int rows = m.length;  
            int cols = n[0].length;  
            int[][] r = new int[rows][cols];  
            for (int i = 0; i < rows; i++) {  
                for (int j = 0; j < cols; j++) {  
                    r[i][j] = 0;  
                    for (int k = 0; k < m[i].length; k++) {  
                        r[i][j] += m[i][k] * n[k][j];  
                    }  
                }  
            }  
            return r;  
        }  
        
        //具体实现矩阵相乘算法
        public static int matrix(int n){
            int[][] m = fb(n); 
            return m[0][1];
        }
        
        public static void main(String[] args){
            System.out.print(max_int_iteration());
            System.out.println();
            System.out.print(max_long_iteration());
            System.out.println();
            System.out.println();
            long t1 = System.currentTimeMillis();  
            long a = recursion(47);
            long t2 = System.currentTimeMillis();
            System.out.println("递归法求斐波那契数:");
            System.out.println(a);
            System.out.println("递归算法Time is: " + (t2 - t1)/1000.0+"秒");
            
            //此处下面可以直接通过给相关类传递参数,实现相应功能,上面的中代码仅仅提供示例
        }
    
    }
    
    
  • 相关阅读:
    springcloud 项目源码 微服务 分布式 Activiti6 工作流 vue.js html 跨域 前后分离
    springcloud 项目源码 微服务 分布式 Activiti6 工作流 vue.js html 跨域 前后分离
    OA办公系统 Springboot Activiti6 工作流 集成代码生成器 vue.js 前后分离 跨域
    java企业官网源码 自适应响应式 freemarker 静态引擎 SSM 框架
    java OA办公系统源码 Springboot Activiti工作流 vue.js 前后分离 集成代码生成器
    springcloud 项目源码 微服务 分布式 Activiti6 工作流 vue.js html 跨域 前后分离
    java 视频播放 弹幕技术 视频弹幕 视频截图 springmvc mybatis SSM
    最后阶段总结
    第二阶段学习总结
    第一阶段学习总结
  • 原文地址:https://www.cnblogs.com/a1439775520/p/13078178.html
Copyright © 2011-2022 走看看