在指定的范圍內,生成不重復的隨機數序列(排除法,篩選法)

b4c2 9年前發布 | 8K 次閱讀 Java

import java.util.ArrayList;
import java.util.List;
import java.util.Random;

/**

  • 在指定的范圍內,生成不重復的隨機數序列 */ public class UnrepeatRandomNumber { private int min; private int max;

    public UnrepeatRandomNumber() {

     this.min = 0;
     this.max = 10;
    

    }

    public UnrepeatRandomNumber(int min, int max) {

     this();
     if (max >= min) {
         this.min = min;
         this.max = max;
     } else {
         System.out.println("max比min小,按缺省值生成UnrepeatRandomNumber對象!");
     }
    

    }

    /**

    • 第一種方法:排除法。隨機生成數字,如果是新生成的數字,則放到結果列表種 否則是已經生成過的,則不加入結果列表,繼續隨機生成。
    • @param length
    • 結果列表的長度
    • @return */ public Integer[] getRandomMethodA(int length) { if (length <= 0) {

       return new Integer[0];
      

      } else if (length > (this.max - this.min)) {

       System.out.println("結果列表長度不能達到:" + length + ", 結果長度只能是:"
               + (this.max - this.min));
       length = this.max - this.min;
      

      } Random rd = new Random();// 用于生成隨機結果 List resultList = new ArrayList(); while (resultList.size() < length) {

       // 將[min, max]區間等價于min + [0, max - min + 1)
       Integer randnum = new Integer(this.min
               + rd.nextInt(this.max - this.min + 1));
       if (!resultList.contains(randnum)) {
           resultList.add(randnum);
       }
      

      } // 使用toArray方法將List轉換成對象數組返回 return (Integer[]) resultList.toArray(new Integer[0]); }

      /**

    • 第二種方法:篩選法。將所有可能被生成的數字放到一個候選列表中。 然后生成隨機數,作為下標,將候選列表中相應下標的數字放到放到結果列表中,
    • 同時,把它在候選列表中刪除。
    • @param length
    • 結果列表的長度
    • @return */ public Integer[] getRandomMethodB(int length) { if (length <= 0) {

       return new Integer[0];
      

      } else if (length > (this.max - this.min)) {

       System.out.println("結果列表長度不能達到:" + length + ", 結果長度只能是:"
               + (this.max - this.min));
       length = this.max - this.min;
      

      } // 初始化候選列表,列表長度為 max -min + 1 int candidateLength = this.max - this.min + 1; List candidateList = new ArrayList(); for (int i = this.min; i <= this.max; i++) {

       candidateList.add(new Integer(i));
      

      }

      Random rd = new Random();// 用于生成隨機下標 List resultList = new ArrayList(); while (resultList.size() < length) {

       // 生成下標,在[0,candidateLength)范圍內
       int index = rd.nextInt(candidateLength);
       // 將候選隊列中下標為index的數字對象放入結果隊列中
       resultList.add(candidateList.get(index));
       // 將下標為index的數字對象從候選隊列中刪除
       candidateList.remove(index);
       // 候選隊列長度減去1
       candidateLength--;
      

      } // 使用toArray方法將List轉換成對象數組返回 return (Integer[]) resultList.toArray(new Integer[0]); }

      public static void outputArray(Integer[] array) { if (array != null) {

       for (int i = 0; i < array.length; i++) {
           System.out.print(array[i] + "  ");
       }
      

      } System.out.println(); }

      public static void main(String[] args) {

      UnrepeatRandomNumber test = new UnrepeatRandomNumber(5, 15); outputArray(test.getRandomMethodA(8)); outputArray(test.getRandomMethodB(8)); // 相比之下,第一種方法利用Random對象生成的隨機數的次數比較多,可能生成了20次數字,才能找到10個不一樣的數字。 // 第二種方法利用Random對象生成的隨機數的次數比較少,需要多少個,就生成多少個,保證了每次生成的數字都不重復。 // 也就是說第一種方法在時間花費上更多。但是第二種方法需要初始化一個候選隊列,需要更多的空間花費。 } } </pre>

 本文由用戶 b4c2 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!