Questo pezzo di codice cerca gli alfieri
Quindi per ogni alfiere eseguo il body di quell'if che, chiaramente, dovrà servire a contare quanti attacchi un alfiere può fare.
Un alfiere può fare al massimo 4 attacchi, perché si può muovere in 4 direzioni: top-left, top-right, bottom-left e bottom-right. Tuttavia, se io posso attaccarti muovendomi bottom-left allora tu puoi attaccarmi top-right perché siamo entrambi alfieri. Quindi nelle prossime righe di codice (all'interno del body) è sufficiente verificare se possiamo attaccare in due direzioni diverse. Io ho scelto bottom-left e bottom-right, ma altre scelte valide potrebbero essere: top-left e top-right, top-left e bottom-left oppure top-right e bottom-right. L'importante è coprire due diagonali diverse, altrimenti una rimane scoperta, verso una sola direzione, perché in una scacchiera con solo alfieri ogni attacco è bidirezionale e non ha senso contare due volte.
Questo controlla la prima diagonale, bottom-right:
L'if serve per controllare se ho trovato un alfiere da attaccare e il break serve ad evitare di attaccare anche gli alfieri coperti dal primo alfiere che incontro. Ci muoviamo bottom-right e, per come stiamo stampando la scacchiera, [0][0] è in alto a sinistra. Muoversi bottom-right vuol dire incrementare entrambi gli indici, sia quello della riga (indice i) che quello della colonna (indice j). Se non trovo nessuno, il for si stoppa appena raggiunge un bordo della scacchiera, ovvero se l'indice di riga incrementato è uguale ad n oppure se l'indice di colonna incrementato è uguale ad n.
In modo del tutto equivalente, controlliamo bottom-left:
L'unica cosa che cambia rispetto a prima è che invece che muoverci verso destra (i.e., incremento l'indice di colonna) ci muoviamo verso sinistra, decrementando l'indice di colonna. Ovviamente, il bordo della scacchiera sarà dall'altro lato.
Chiaro? Prova a leggere con calma.
C:
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
if (board[i * n + j]) {
// ...
}
}
}
Un alfiere può fare al massimo 4 attacchi, perché si può muovere in 4 direzioni: top-left, top-right, bottom-left e bottom-right. Tuttavia, se io posso attaccarti muovendomi bottom-left allora tu puoi attaccarmi top-right perché siamo entrambi alfieri. Quindi nelle prossime righe di codice (all'interno del body) è sufficiente verificare se possiamo attaccare in due direzioni diverse. Io ho scelto bottom-left e bottom-right, ma altre scelte valide potrebbero essere: top-left e top-right, top-left e bottom-left oppure top-right e bottom-right. L'importante è coprire due diagonali diverse, altrimenti una rimane scoperta, verso una sola direzione, perché in una scacchiera con solo alfieri ogni attacco è bidirezionale e non ha senso contare due volte.
Questo controlla la prima diagonale, bottom-right:
C:
// test for down-right diagonal attacks
for (int k = 1; i + k < n && j + k < n; k++) {
if (board[(i + k) * n + (j + k)]) {
result++;
break;
}
}
In modo del tutto equivalente, controlliamo bottom-left:
C:
// test for down-left diagonal attacks
for (int k = 1; i + k < n && 0 <= j - k; k++) {
if (board[(i + k) * n + (j - k)]) {
result++;
break;
}
}
Chiaro? Prova a leggere con calma.