0

I am using Java and working on 5X5 board game(represented as String[][]) and I looking for an efficient way to randomly place 3 "A"'s, 3 "B",s 3 "C"'s, 3 "D"'s on the board.

I thought about using a nested for loop inside of a while loop to go over each slot, and randomly assign letters to 'slots' on the board, but I want to possibly do it in one pass of the board, if there is a good way to randomly place all 15 letters on the board in one pass.

Any suggestions?

2 Answers 2

1

You can use an ArrayList to store the letters (and the empty cells, I'm using a dot . so you can recognize it in the output), then use Collections.shuffle() to put elements of the ArrayList in "random" places. Finally assign each letter to the String[][] array:

public static void main(String[] args)
{
    String[][] board = new String[5][5];
    List<String> letters = new ArrayList<>();

    // fill with letters
    for (int i = 0; i < 3; i++) {
        letters.add("A");
        letters.add("B");
        letters.add("C");
        letters.add("D");
        letters.add("E");
    }
    // fill with "empty"
    for (int i = 0; i < 10; i++) {
        letters.add(".");
    }

    Collections.shuffle(letters);

    for (int i = 0; i < board.length; i++) {
        for (int j = 0; j < board.length; j++) {
            board[i][j] = letters.get(i*board.length + j);
        }
    }

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

Output Sample:

C B . . . 
A E . E A 
. A . D D 
C . . . D 
B C E . B 

Note:

The operation i*board.length + j will generate consequent numbers 0, 1, 2, 3, ... 24 en the nested loop.

Sign up to request clarification or add additional context in comments.

Comments

1

One way: create an ArrayList<Character> or of String, feed it the 15 letters, call java.util.Collections.shuffle(...) on the ArrayList, and then iterate over this List, placing its randomized items into your array.

e.g.,

  List<String> stringList = new ArrayList<String>();
  for (char c = 'A'; c <= 'E'; c++) {
     for (int i = 0; i < 3; i++) {
        stringList.add(String.valueOf(c));
     }
  }
  for (int i = 15; i < 25; i++) {
     stringList.add(null);
  }

  Collections.shuffle(stringList);
  String[][] gameBoard = new String[5][5];
  for (int i = 0; i < gameBoard.length; i++) {
     for (int j = 0; j < gameBoard[i].length; j++) {
        gameBoard[i][j] = stringList.get(i * gameBoard.length + j);
     }
  }

  // now test it
  for (int i = 0; i < gameBoard.length; i++) {
     for (int j = 0; j < gameBoard[i].length; j++) {
        System.out.printf("%-6s ", gameBoard[i][j]);
     }
     System.out.println();
  }

4 Comments

Better still, populate it with 15 letters and 10 nulls (or empty strings, or some other thing that means "nothing").
@DavidWallace: ah, I didn't see that he needed empty spaces. I wonder if this suggestion would fail then if you tried to shuffle a list with nulls in it. I fear that it would. Instead, use a marker char, say ! or (char) 0.
I don't see why it would fail with nulls in the list. But my usual answer to such question is "test it and find out".
Why nest loops when you populate gameBoard? Why not just write gameBoard[i] = stringList.subList(i*5, i*5+5).toArray(new String[0]); inside a single (unnested) loop?

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.