| Bytes | Lang | Time | Link |
|---|---|---|---|
| 045 | Uiua | 240908T195017Z | nyxbird |
| 103 | x86 machine code | 191219T110118Z | Dmitry S |
| 125 | Ruby | 160810T231702Z | Level Ri |
| 130 | JavaScript ES6 | 160811T115233Z | Neil |
| 289 | Java 8 lambda | 160810T215524Z | Frozn |
| 209 | Ruby | 160810T220919Z | MegaTom |
Uiua, 45 bytes
⊡⊗:"QRBNK":⍜≡⊡⊸↥:+@.[↥,,⊃(/↥=0|/=|=2/×|=1/↥)]⌵-°⍉⇡8_8⟜¤
⇡8_8 # coordinates of an 8x8 grid
⌵-°⍉ # the absolute difference of each x and y from the point
[ ⊃( )] # push an array of boolean arrays with the coordinates that have:
|=1/↥ # a max distance of 1 (king)
|=2/× # a product of 2 (knight)
|/= # equal values (bishop)
/↥=0 # a zero (rook)
↥,, # a 1 in one of the previous two arrays (queen)
+@. # convert into .s and /s
⍜≡⊡ ↥: ⟜¤ # put the piece's char into each array
⊡⊗:"QRBNK": ⊸ # pick the array with the corresponding index in "QRBNK"
This feels too long (mainly in the ⊃).
x86 machine code, 114 103 bytes
Input:
- AL - ASCII piece type (N/B/R/Q/K)
- BP - 0x88 index
- DI - Buffer
Output:
- DI - Last character + 1
Assembly source code:
pusha
mov di, offset disp_db - 3
mov cx, 8
mov bx, cx
repne scasb
mov dx, di
sub dx, offset disp_db - 1
pop si
mov di, si
init_loop:
mov ax, '.'
mov cl, 8
rep stosb
mov al, 9
mov cl, 7
rep stosb
inc ax
stosb
dec bx
jnz init_loop
init_done:
push di
mov di, si
piece_loop:
mov si, offset moves_knight - 2
add si, dx
lodsb
add si, ax
vec_loop:
lodsb
cbw
sign_loop:
mov bx, bp
dest_loop:
add bx, ax
test bl, 088h
jnz vec_cont
mov byte ptr [di + bx], '*'
test dl, dl
jp dest_loop
vec_cont:
neg ax
js sign_loop
cmp al, 80h
jnz vec_loop
done:
popa
mov [di + bp - 128], al
ret
disp_db db "NBKRQ"
moves_knight db vec_knight - moves_knight - 1
moves_bishop db vec_bishop - moves_bishop - 1
moves_king db vec_king - moves_king - 1
moves_rook db vec_rook - moves_rook - 1
moves_queen db vec_king - moves_queen - 1
vec_knight db 0Eh, 12h, 1Fh, 21h, 80h
vec_bishop db 0Fh, 11h, 80h
vec_king db 0Fh, 11h
vec_rook db 01h, 10h, 80h
Ruby, 125
anonymous function, prints to stdout.
RevB: golfed, but a bug fix brought it back to the same length as before.
->x,y,z{72.times{|i|v=y-i/9;u=x-i%=9
e=u*u+v*v
$><<(i<8?e<1?z:[r=0==v*u,b=u*u==v*v,b|r,3>e,5==e]["RBQKN"=~/#{z}/]??*:?.:$/)}}
Prints each of the 64 squares + 8 newlines = 72 characters individually. Relies on e, the square of the Euclidean distance between the current square and the given coordinates for checking king moves and knight moves (and also for printing the piece value z when the Euclidean distance is zero.)
Ungolfed in test program
f=->x,y,z{ #x,y,character
72.times{|i| #8 rows of (8 chars + newline) = 72 chars
v=y-i/9; #vertical diff between y coord and current square
u=x-i%=9 #horizontal diff between x coord and current square. note i%=8
e=u*u+v*v #square of euclidean distance
$><<( #$> is stdout. send to it....
i<8? #if not the newline column,
e<1?z: #if the euclidean distance is 0, print the symbol for the piece, else
[r=0==v*u, #TRUE if v or u is 0 (rook)
b=u*u==v*v, #TRUE if abs(u)==abs(v) (bishop)
b|r, #TRUE if either of the above are true (queen)
3>e, #TRUE if e == 1 or 2 (king)
5==e #TRUE if e == 5 (knight)
]["RBQKN"=~/#{z}/]??*:?.: #select value from array corresponding to piece and print * or . accordingly
$/ #if newline column, print a newline
)
}
}
x=gets.to_i
y=gets.to_i
z=gets.chomp
f[x,y,z]
JavaScript (ES6), 137 130 bytes
f=
(x,y,p)=>`${1e8}`.repeat(8).replace(/./g,c=>+c?(i=x*x--,z=y,`
`):i+(j=z*z--)?`.*`[+!{K:i+j>3,N:i+j-5,R:i*j,B:b=i-j,Q:b*i*j}[p]]:p)
;
<div onchange=if(+x.value&&+y.value&&p.value)o.textContent=f(x.value,y.value,p.value)><input id=x type=number placeholder=X><input id=y type=number placeholder=Y><select id=p><option value=>Piece<option value=B>Bishop<option value=K>King<option value=N>Knight<option value=Q>Queen<option value=R>Rook</select><div><pre id=o></pre>
Note: Outputs one leading newline.
Explanation: Builds and scans though the string 100000000100000000100000000100000000100000000100000000100000000100000000. Each 1 indicates a new line where the relative coordinate x is decremented and the relative coordinate z is reset. Each 0 indicates a new square where the relative coordinate z is decremented. (y is reserved to reset z.) Then uses the fact that many of the moves can be categorised by the squares i and j of the relative coordinates (before they were decremented):
- (initial square)
i + j == 0 - B:
i == j - K:
i + j < 3 - N:
i + j == 5 - Q:
i == j || !i || !j - R:
!i || !j
Because - is shorter than == it's golfier to compute the negation and invert it later. (This lets me use the cute '.*'[] expression although it's actually the same length as a boring ?: expression.) * is also golfier than &&.
Java 8 lambda, 473 435 289 characters
Looks like this:
(R,C,f)->{String b="";for(int r=0,c,d,D;r<8;r++){for(c=0;c<8;c++){d=R-r<0?r-R:R-r;D=C-c<0?c-C:C-c;b+=R==r&&C==c?f:((f=='R'||f=='Q')&&(R==r||C==c))||((f=='B'||f=='Q')&&d==D)||(f=='K'&&((R==r&&D==1||C==c&&d==1)||(d==D&&d==1)))||(f=='N'&&(d==2&&D==1||d==1&&D==2))?"M":".";}b+="\n";}return b;}
Or ungolfed into a class:
public class Q89429 {
static String chessMoves(int row, int column, char figure) {
String board = "";
for (int r = 0, c, deltaRow, deltaColumn; r < 8; r++) {
for (c = 0; c < 8; c++) {
deltaRow = row - r < 0 ? r - row : row - r;
deltaColumn = column - c < 0 ? c - column : column - c;
board += row == r && column == c ?
figure :
((figure == 'R' || figure == 'Q') && (row == r || column == c))
|| ((figure == 'B' || figure == 'Q') && deltaRow == deltaColumn)
|| (figure == 'K' && (
(row == r && deltaColumn == 1 || column == c && deltaRow == 1)
|| (deltaRow == deltaColumn && deltaRow == 1)))
|| (figure == 'N' && (deltaRow == 2 && deltaColumn == 1 || deltaRow == 1 && deltaColumn == 2))
? "M" : ".";
}
board += "\n";
}
return board;
}
}
This is a TriFunction. It returns the chess field as a printable String. I wanted to use streams, and it looks quite good. It's like a 2D iteration, may be shorter without the streams. Switched to classic loops and saved a lot!
It can definitely be shortened by using a ternary, I will do that now.
Updates
Saved 38 characters by using a ternary.
Saved 146 characters by using good old loops. We should all abandon streams ;)
Ruby, 209 Bytes
->v,a,b{R=->x,y{x==a||y==b};B=->x,y{x-y==a-b||a-x==y-b};Q=->x,y{R.(x,y)||B.(x,y)};K=->x,y{((x-a).i+y-b).abs<2};N=->x,y{((a-x)*(b-y)).abs==2};(r=(0..7)).map{|x|r.map{|y|[x,y]==[a,b]?v: eval(v+".(x,y)??x:?o")}}}
This is a lambda that makes use of other lambdas, defined inside.