Как это сделать для l oop со всеми возможными комбинациями пар (+ - 1, + - 2) - PullRequest
0 голосов
/ 01 мая 2020

Я рисую возможные пути коня в шахматах, и один случай выглядит следующим образом:

if (boundsOK(x + 1, y + 2)) {
    temp = boardArray[x + 1][y + 2];

    if (isLegalMove(x, y, x + 1, y + 2) != MoveType.NONE) {
        moves.add(x);
        moves.add(y);
        moves.add(x + 1);
        moves.add(y + 2);

        move(x + 1, y + 2, x, y);
    }
    boardArray[x + 1][y + 2] = temp;
}

Теперь вместо 1 и 2 я хочу построить al oop, который бы опробовал комбинации :

 1  2

-1  2

 1 -2

-1 -2


 2  1

-2  1

 2 -1

-2 -1

Но я не знаю, как это сделать без лишних «если». Есть хотя бы умный способ сделать это?

1 Ответ

2 голосов
/ 01 мая 2020

Вы можете создать класс Vector или аналогичный (или использовать любой парный тип), заполнить список своими значениями и выполнить итерации по нему (не обращая особого внимания на производительность):

var moves = List.of(
        new Move(1,2),
        new Move(-1,2),
        new Move(1,-2),
        new Move(-1,-2),
        new Move(2,1),
        new Move(-2,1),
        new Move(2,-1),
        new Move(-2,-1));

for (var move : moves) {
    var x = move.getX();
    var y = move.getY();
    testMove(x, y) … // or refactor your method to receive a Move instance directly
}

Если вы действительно пытаетесь сохранить некоторые строки (вы играете в гольф?), Вы можете создать экземпляры с помощью al oop, но это не сделает код лучше (ни с точки зрения читабельности, ни с точки зрения производительности). или от количества символов для ввода):

var moves = new ArrayList<Move>();
for (int x : List.of(1,-1)) {
    for (int y : List.of(2,-2)) {
        moves.add(new Move(x,y));
    }
}
for (int x : List.of(2,-2)) {
    for (int y : List.of(1,-1)) {
        moves.add(new Move(x,y));
    }
}

Подумав еще немного, его можно сжать до 2 циклов и 1 условного, если мы заметим тот факт, что ходы всегда имеют содержать числа 1 и 2, и там никогда не будет ходов (± 1, ± 1) или (± 2, ± 2):

var moves = new ArrayList<Move>(8);
var offsets = List.of(-2,-1,1,2);
for (int x : offsets) {
    for (int y : offsets) {
        if (Math.abs(x) != Math.abs(y)) {
            moves.add(new Move(x,y));
        }
    }
}

Но все же я думаю, что это благоприятно для go KISS (будь проще, глупый) маршрут и просто выпиши все возможные ходы. Намерение сразу ясно, и оно примерно столько же строк (и вам не нужно придумывать хитрые способы «вычислить» ходы).

...