1. 程式人生 > >算法學習——遞推之超級素數

算法學習——遞推之超級素數

mat 定義 開始 思路 src 通過 分享圖片 pub next

算法描述

超級素數定義:

  1. m位超級素數本身是素數
  2. 最高位開始,去掉一位為m-1位的素數……

例: 103不是超級素數,去掉最高位的1之後為3,不是有個2位素數,137是一個三位超級素數,去掉最高位1之後為37,37是一個二位素數,去掉3之後為7,7也是一個素數

要求: 輸入整數m(1 < m<=10),統計m位超級素數的個數,並輸出其中最大的m位超級素數

算法思路

  1. 設置一個判斷素數的方法

  2. 1位素數只有3個,3,5,7,我們可以推測,2位超級素數的個位數只能是3,5,7,沒有其他的選擇了,同理,3位超級素數的十位和個位數只能是二位的超級素數組成,由此我們就可以得到一個遞推關系

算法實現

    Scanner scanner = new Scanner(System.in);
    int m = scanner.nextInt();
    scanner.close();
    int a[] = new int[10000];
    int b[] = new int[10000];
    int count =0;//統計超級素數的個數
    
    int g = 3;//記錄每一個位的超級素數,當前記錄的是個位的3個超級素數,3,5,7 之後每一位都會重新賦值
    a[0] = 3;
    a[1] = 5;
    a[2]=7;
    
    //i表示十位,所以這裏i要小於m
    for(int i=1;i<m;i++){
        int t =0;
        int  e =  (int) Math.pow(10, i);//表示十位,百位…… 每一個位的階乘
        //j*e 10,20…… 100,200……
        for(int j=1;j<=9;j++){
            //遍歷a數組的全部素數
            for(int k=0;k<g;k++){
                if(panduan(e*j+a[k])){
                    b[t] = e * j +a[k];
                    t++;//統計在當前位的超級素數的個數,之後再賦值給g                 
                    if(i==m-1){
                        count++;//統計
                    }
                }
            }
        }
        g=t;
        //將b數組中的數據轉移動a數組中,便於之後的遞推
        for(int z=0;z<g;z++){
            a[z] = b[z];
        }
        
    }
    
    System.out.println(count);
    //冒泡排序,輸出最大值
    for(int i=0;i<a.length-1;i++){
        for(int j=i+1;j<a.length;j++){
            if(a[i]<a[j]){
                int t = a[i];
                a[i]=a[j];
                a[j]=t;
            }
        }
    }
    System.out.println(a[0]);
}

/**
 * 
 * @param a
 * @return 通過試商法判斷a是否為素數
 */
public static boolean panduan(int a){
    
        int s = (int)Math.sqrt(a);
        
            for(int i=2;i<=s;i++){
                if(a%i==0){
                    return false;
                }
            }
            return true;
        
}

結果

技術分享圖片

算法學習——遞推之超級素數