|
1 | 1 | #include <stdio.h> |
2 | 2 |
|
3 | 3 | #define I if( |
4 | | -#define M )break; |
5 | | -#define N for( |
6 | | -#define Q 99999 |
| 4 | +#define K )break; |
| 5 | +#define F for( |
| 6 | +#define H 99999 |
7 | 7 | #define Z ;if(!strncmp(c, |
8 | 8 |
|
9 | | -char c[Q], *C, |
| 9 | +char c[H], *C, |
10 | 10 | *T="#5)-57234#15BD#24#24$3#EKFA\\FKE/.2##$"; // Piece move steps, board setup data and promotion XORs (subtract '#'=35). |
11 | 11 |
|
12 | | -B[Q], R, S, W, X; |
| 12 | +B[H], E, S, X, Y; |
13 | 13 |
|
14 | | -F(U, V, p, r) { |
15 | | - int f=0,t, i, d, P, u, q; |
16 | | - N ;f<128;f=f+9&~8) { // Loop over squares looking for pieces. |
17 | | - N i=T[(P=B[f])&7]-35,d=0;d<0 || (d=T[i++]-35);d=-d) { // Loop over move steps for this piece. |
18 | | - N t=f;!((t+=d)&(q=136)) && P&S;) { // Loop over destination squares in this direction. |
| 14 | +D(x, y, p, e) { |
| 15 | + int f=0,t, i, d, m, v, b; |
| 16 | + F ;f<128;f=f+9&~8) { // Loop over squares looking for pieces. |
| 17 | + F i=T[(m=B[f])&7]-35,d=0;d<0 || (d=T[i++]-35);d=-d) { // Loop over move steps for this piece. |
| 18 | + F t=f;!((t+=d)&(b=136)) && m&S;) { // Loop over destination squares in this direction. |
19 | 19 | // Friendly capture? |
20 | | - I (u=B[t])&S M |
| 20 | + I (v=B[t])&S K |
21 | 21 |
|
22 | 22 | // Special pawn logic. |
23 | | - I P%8==2) |
| 23 | + I m%8==2) |
24 | 24 | { |
25 | 25 | I ((d>0)^(S==32)) || // Bad direction? |
26 | | - (!u && d%2 && t!=r) | // Diagonal without capture? |
27 | | - (!(d%2) && u>0) // Straight with capture? |
28 | | - M |
| 26 | + (!v && d%2 && t!=e) | // Diagonal without capture? |
| 27 | + (!(d%2) && v>0) // Straight with capture? |
| 28 | + K |
29 | 29 |
|
30 | | - I t==r) q=t^16; // Is this an en-passent capture? |
| 30 | + I t==e) b=t^16; // Is this an en-passent capture? |
31 | 31 | } |
32 | 32 |
|
33 | 33 | // Other side left in check? |
34 | | - I U==8 && u&16) |
| 34 | + I x==8 && v&16) |
35 | 35 | return 0; |
36 | 36 |
|
37 | 37 | // Make move. |
38 | | - B[t]=P%128; |
39 | | - B[f]=B[q]=0; // If en-passent capture, remove victim pawn. |
40 | | - I P%8==2 && (t<8 || t>103)) |
| 38 | + B[t]=m%128; |
| 39 | + B[f]=B[b]=0; // If en-passent capture, remove victim pawn. |
| 40 | + I m%8==2 && (t<8 || t>103)) |
41 | 41 | B[t]^=T[p%7+31]-35; // Promotion. |
42 | 42 | S^=96; |
43 | | - I P&16 && t!=f+d) |
| 43 | + I m&16 && t!=f+d) |
44 | 44 | B[f+t>>1]=B[t+(d*3-1)/2],B[t+(d*3-1)/2]=0; // If castling also move rook. |
45 | 45 |
|
46 | 46 | // Looking to make a move? (if our own move, make sure does not leave us in check) |
47 | | - I (t==V && f==U) | (U==Q && F(8,0,0,Q))) { |
48 | | - W=f,X=t; |
49 | | - R=(P%8==2 && t!=f+d ? f+t>>1 : 9); // Set ep-target square if double pawn move. |
50 | | - return B[t]==P%128; // Indicate if promotion has NOT occured. |
| 47 | + I (t==y && f==x) | (x==H && D(8,0,0,H))) { |
| 48 | + X=f,Y=t; |
| 49 | + E=(m%8==2 && t!=f+d ? f+t>>1 : 9); // Set ep-target square if double pawn move. |
| 50 | + return B[t]==m%128; // Indicate if promotion has NOT occured. |
51 | 51 | } |
52 | 52 |
|
53 | 53 | // Undo move. |
54 | | - B[q]=10|S; // If en-passent capture, replace victim pawn. |
| 54 | + B[b]=10|S; // If en-passent capture, replace victim pawn. |
55 | 55 | S^=96; |
56 | | - B[f]=P; |
57 | | - B[t]=u; |
| 56 | + B[f]=m; |
| 57 | + B[t]=v; |
58 | 58 |
|
59 | | - I (P&16 && f==U && t+d==V) | // If GUI has given us a castling move, |
60 | | - (P&128 && t==f+d && !(d%2))) // or double pawn first move, loop once more. |
| 59 | + I (m&16 && f==x && t+d==y) | // If GUI has given us a castling move, |
| 60 | + (m&128 && t==f+d && !(d%2))) // or double pawn first move, loop once more. |
61 | 61 | continue; |
62 | 62 |
|
63 | 63 | // Hit a piece or non-slider? |
64 | | - I u || P&8 M |
| 64 | + I v || m&8 K |
65 | 65 | } |
66 | 66 | } |
67 | 67 | } |
68 | 68 | return 1; |
69 | 69 | } |
70 | 70 |
|
71 | 71 | main(i) { |
72 | | - N ;strtok(gets(c)," ");fflush(stdout)) { // Loop, grabbing input and flushing output. |
| 72 | + F ;strtok(gets(c)," ");fflush(stdout)) { // Loop, grabbing input and flushing output. |
73 | 73 | Z"uci",4)) puts("id name i\nid author D\nuciok") // Reply to 'uci'. |
74 | 74 | Z"i",1)) puts("readyok") // Reply to 'isready'. |
75 | 75 | Z"p",1)) { // Parse 'position' command. |
76 | | - N i=0;i<8;++i) // Reset board to start position. |
77 | | - B[i+16]=R=170,B[i+96]=202, // Pawns. |
| 76 | + F i=0;i<8;++i) // Reset board to start position. |
| 77 | + B[i+16]=E=170,B[i+96]=202, // Pawns. |
78 | 78 | B[i]=(B[i+112]=T[i+23])-(S=32), // Pieces. |
79 | 79 | B[i+S]=B[i+48]=B[i+64]=B[i+80]=0; // Empty rows. |
80 | | - N ;C=strtok(0," ");) |
81 | | - F(*C+C[1]*16-881, C[2]+C[3]*16-881, C[4], R); |
| 80 | + F ;C=strtok(0," ");) |
| 81 | + D(*C+C[1]*16-881, C[2]+C[3]*16-881, C[4], E); |
82 | 82 | } |
83 | 83 | Z"g",1)) // Go command. Make a move and print it. |
84 | | - i=F(Q, 0, 0, R), |
85 | | - printf("bestmove %c%i%c%i%c\n", W%16+97, W/16+1, X%16+97, X/16+1, i?32:98); |
| 84 | + i=D(H, 0, 0, E), |
| 85 | + printf("bestmove %c%i%c%i%c\n", X%16+97, X/16+1, Y%16+97, Y/16+1, i?32:98); |
86 | 86 | } |
87 | 87 | } |
0 commit comments