简体   繁体   中英

Generating an array of non-repeating integers

I'm trying to generate an array of 5 non-repeating integers in Java, but there are still repeats when I run it. Here's my code so far:

public int[] generateCode(){
    code[0] = (int)Math.round(Math.random()*8+1); // initialize first number so it won't be compared against 
    for(int i=1; i<code.length; i++){
        code[i] = (int)Math.round(Math.random()*8)+1;
        for(int j=0; j<i; j++){
            while(code[i]==code[j]){
                code[i] = (int)Math.round(Math.random()*8)+1;
            }
        } // end inner for loop
        
    } // end outer for loop
    return code;
    
    
} // end generateCode method

Any help is very much appreciated!

So, your for-loop is checking for repeated characters, BUT each time you generate a new value (in the while-loop ) you're not checking to see if the value exits before j .

There are a number of possible ways you might address this issue, I prefer ones which uses Collections.shuffle , but assuming that you can't use features like Arrays , Collections , List , Set or possibly even streams, we need to work with what we have, arrays.

Since you have a small range of acceptable values which need to fit into an even smaller range, a simple solution might be to generate a "master" list of allowed values and randomly select a value from the master list, tracking which values you've already picked.

Sounds more complicated then it actually is, for example...

public int[] generateCode() {
    int[] masterValues = new int[] { 1, 2, 3, 4, 5, 6, 7, 8, 9 };
    int[] codes = new int[5];
    
    Random rnd = new Random();
    int index = 0;
    while (index < codes.length) {
        int lookupIndex = 0;
        do {
            lookupIndex = rnd.nextInt(masterValues.length);
        } while (masterValues[lookupIndex] == 0);
        codes[index] = masterValues[lookupIndex];
        masterValues[lookupIndex] = 0;
        index++;
    }
    return codes;
}

This creates a "master" list of values. It then randomly calculates a "lookup" index, checks to see if the value in the master list is 0 or not, if not, it assigns it to the next index in the codes array and sets the value in the master list to 0 , otherwise it generates a new random index and tries again. This all repeats till it fills the codes array

So doing something like...

System.out.println(Arrays.toString(generateCode()));
System.out.println(Arrays.toString(generateCode()));
System.out.println(Arrays.toString(generateCode()));
System.out.println(Arrays.toString(generateCode()));

could print (because it's "random")...

[8, 1, 4, 7, 5]
[9, 6, 2, 1, 8]
[6, 5, 9, 4, 7]
[2, 5, 3, 1, 4]

There are much easier ways to do this. Using a Set<Integer> would be one. Here is another.

List<Integer> list = new ArrayList<>(List.of(1,2,3,4,5,6,7,8));
Collections.shuffle(list);
System.out.println(list.subList(0,5));

prints something like

[4, 5, 8, 2, 1]

As was pointed out to me, you may not be allowed to use or know about collections. But I would recommend you at least make a helper method to check for duplicates to reduce the clutter. Something like the following:

public boolean contains(int[] arr, int n) {
    for (int v : arr) {
        if (v == n) {
          return true;
        }
    }
    return false;
}

Then you can keep checking the current value to be false before you add it. Once it works it also lets you focus on other aspects of your code.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM