Morpion solitaire: Difference between revisions
Content added Content deleted
mNo edit summary |
(→{{header|REXX}}: reduce the program size, elided code to support boxing of the grid, added/changed comments, simplified code.) |
||
Line 1,046: | Line 1,046: | ||
<br>This program allows the <tt> D </tt> or <tt> T </tt> forms of the game, and allows any board size (grid size) of three or higher. |
<br>This program allows the <tt> D </tt> or <tt> T </tt> forms of the game, and allows any board size (grid size) of three or higher. |
||
<br>The default games is <tt> 5T </tt> |
<br>The default games is <tt> 5T </tt> |
||
<lang rexx>/*REXX program plays Morpion solitaire (with grid output), the default is the 5T version*/ |
|||
signal on syntax; signal on noValue /*handle possible REXX program errors. */ |
|||
/* [↓] handle the user options (if any)*/ |
|||
prompt= /*null string is used for ERR return.*/ |
|||
quiet= 0 /*flag: suppresses output temporarily.*/ |
|||
oFID= 'MORPION' /*filename of the game's output file. */ |
|||
arg game player seed . /*see if a person wants to play. */ |
|||
if game=='' | game=="," then game= '5T' /*Not specified? Then use the default.*/ |
|||
if player=='' | player=="," then player= /* " " " " " " */ |
|||
if isInt(seed) then call random ,,seed /*Is integer? Then use for RANDOM seed*/ |
|||
TorD= 'T (touching) ───or─── D (disjoint).' /*the valid game types (T or D). */ |
|||
sw= linesize() - 1 /*SW = screen width ─or─ linesize. */ |
|||
gT= right(game, 1) /*T = touching ─or─ D = disjoint.*/ |
|||
if \datatype(gT,'U') | verify(gT, "GT")\==0 then call err 'game not G or T' /*error?*/ |
|||
gS= left( game, length(game) - 1) /*gS=Game Size (line length for a win)*/ |
|||
if \isInt(gS) then call err "game size isn't an integer:" gS /*error?*/ |
|||
gS= gS / 1 /*normalize the value of GS. */ |
|||
if gS<3 then call err "grid size is too small for Morpion solitaire :" gS /*error? */ |
|||
/*handle the defaults/configuration. */ |
|||
indent= left('', max(0, sw - gS - 10) % 2) /*indentation used for board display. */ |
|||
indent= ' ' |
|||
empty= 'fa'x /*the empty grid point symbol (glyph). */ |
|||
@.= empty /*the field (grid) is infinite in size*/ |
|||
CBLF= player \== '' /*playing with a carbon─based lifeform?*/ |
|||
if CBLF then oFID= player /*oFID: the fileID for the game LOG. */ |
|||
oFID= oFID'.LOG' /*full name for the LOG's filename. */ |
|||
prompt= 'enter X,Y point and an optional character for placing on board (or Quit):' |
|||
prompt= right(prompt, sw, '─') /*right justify the prompt message. */ |
|||
call GreekX /*draw the (initial) Greek cross. */ |
|||
do #=1 for 1500 /*───play a game of Morpion solitaire. */ |
|||
<lang rexx>/*REXX program to play Morpion solitaire, the default is the 5T version.*/ |
|||
if CBLF then do |
|||
signal on syntax; signal on novalue /*handle REXX program errors. */ |
|||
if Gshots\=='' then do; parse var Gshots shot Gshots |
|||
quiet=0; oFID='MORPION' |
|||
parse var shot gx ',' gy |
|||
call mark gx,gy |
|||
if game=='' | game==',' then game='5T' /*Not specified? Then use default*/ |
|||
iterate |
|||
end |
|||
TorD='T (touching) ───or─── D (disjoint).' /*valid games types (T | D).*/ |
|||
if Gshots=='' then leave /*#*/ |
|||
call t prompt; pull stuff; stuff= translate(stuff, , ',') |
|||
if \datatype(gT,'U') | verify(gT,gT)\==0 then call err 'game gT not' gT |
|||
stuff= space(stuff); parse var stuff px py p |
|||
gS=left(game,length(game)-1) /*gS=Game Size (line len for win)*/ |
|||
_= px; upper _; if abbrev('QUIT', _, 1) then exit /*quitting? */ |
|||
if \datatype(gS,'W') then call err "game size isn't numeric:" gS |
|||
if stuff=='' then do; call display; iterate |
|||
gS=gS/1 |
|||
end |
|||
if gS<3 then call err "grid size is too small:" gS |
|||
call mark px,py,p |
|||
sw=linesize()-1 |
|||
end /*if CBLF*/ |
|||
indent=left('',max(0,sw-gS-10)%2) /*indentation used board display.*/ |
|||
else do; quiet= 1; shot= translate( word(Gshots, turn), , ',') |
|||
if shot=='' then do 50 |
|||
xr= loX -1 + random(0, hiX - loX + 2) |
|||
yr= loY -1 + random(0, hiY - loY + 2) |
|||
if @.xr.yr\==empty then iterate |
|||
if \neighbor(xr, yr) then iterate |
|||
shot= xr yr |
|||
prompt='enter X,Y point and an optional character for placing on board', |
|||
end /*50*/ |
|||
'(or Quit):'; prompt=right(prompt,sw,'─') /*right justify it.*/ |
|||
call mark word(shot, 1), word(shot, 2) |
|||
call GreekCross |
|||
end /*else*/ |
|||
jshots=Gshots |
|||
end /*#*/ |
|||
call display |
|||
do turns=1 for 1000 |
|||
call t '* number of wins =' wins |
|||
if CBLF then do |
|||
exit wins /*stick a fork in it, we're all done. */ |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
parse var stuff px py p |
|||
Gshot: if arg()==2 then Gshots= space(Gshots arg(1)','arg(2) ); return |
|||
_=px; upper _; if abbrev('QUIT',_,1) then exit |
|||
isInt: return datatype( arg(1), 'W') /*is int? */ |
|||
isNum: return datatype( arg(1), 'N') /*is num? */ |
|||
call mark px,py |
|||
t: say arg(1); call lineout oFID,arg(1); return |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
else do; quiet=1 |
|||
?win: arg z; L= length(z) |
|||
shot=translate(word(Gshots,turn),,',') |
|||
if |
if L>gS then do; if gT=='D' then return 0 /*longlines ¬ kosker for D*/ |
||
parse var z z1 '?' z2 /*could be xxxxx?xxxx */ |
|||
return length(z1)>=4 | length(z2)>=4 |
|||
end |
|||
return L==gS |
|||
if \neighbor(xr,yr) then iterate |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
shot=xr yr |
|||
display: call t; do y=hiY to loY by -1; _c= /*start at a high Y. */ |
|||
do x=loX to hiX; != @.x.y; _c= _c || ! /*build an "X" grid line. */ |
|||
call mark word(shot,1),word(shot,2) |
|||
end |
end /*x*/ |
||
call t indent _c /*display a grid line. */ |
|||
end /*turns*/ |
|||
end /*y*/ |
|||
if wins==0 then call t copies('═', sw) |
|||
call t '* number of wins =' wins |
|||
else call t right('(above) the board after' wins "turns.", sw, '═') |
|||
call t |
|||
/*───────────────────────────────error handling subroutines and others.─*/ |
|||
return |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
call t center(' error! ',max(40,linesize()%2),"*"); call t |
|||
err: if \quiet then do; call t; call t |
|||
call t center(' error ', max(40, sw % 2), "*"); call t |
|||
do j=1 for arg(); call t arg(j); call t; end; call t |
|||
if prompt=='' then exit 13; return |
|||
end |
|||
if prompt=='' then exit 13; return |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
GreekX: wins= 0; loX= 1; hiX= 0; LB= gS - 1 /*Low cross Beam. */ |
|||
turn= 1; loY= 1; hiY= 0; HT= 4 + 3*(LB-2) /*─ ─ */ |
|||
Lintel= LB - 2; Gshots=; TB= HT - LB + 1 /*Top cross Beam. */ |
|||
$= '0f'x; @@.= /*─ ─ */ |
|||
do y=1 for HT; ToB= $ || copies($, Lintel) || $ /*ToB: Top Or Bot.*/ |
|||
beam= $ || copies($, Lintel)$ || left('', Lintel)$ || copies($, Lintel) || $ |
|||
select /*$: Greek cross glyph*/ |
|||
when y==1 | y==HT then do x=1 for LB; call place x+LB-1,y,substr(ToB, x, 1) |
|||
end |
|||
when y==LB | y==TB then do x=1 for HT; if x>LB & x<TB then iterate |
|||
call place x,y,substr(beam, x, 1) |
|||
end |
|||
when y>LB & y<TB then do x=1 by HT-1 for 2; call place x,y,$; end |
|||
otherwise do x=LB by TB-LB for 2; call place x,y,$; end |
|||
end /*select*/ |
|||
end /*y*/ |
|||
@abc= 'abcdefghijklmnopqrstuvwxyz'; @chars= '1234567890'translate(@abc) || @abc |
|||
novalue: syntax: prompt=; quiet=0 |
|||
@@.63= '@' ; @@.64= "æÆα"; @@.67= 'ß' ; @@.68= "¢" ; @@.69= '^' |
|||
call err 'REXX program' condition('C') "error",, |
|||
@@.70= 'Σ' ; @@.71= "ƒ" ; @@.72= 'ñÑπ'; @@.75= "σΘφ"; @@.78= '₧' |
|||
condition('D'),'REXX source statement (line' sigl"):",, |
|||
@@.79= '$δ'; @@.81= "¥" ; @@.82= '#%&*=+\;' |
|||
do j=60 to 99; @chars= @chars || @@.j |
|||
end /*j*/ |
|||
@chars= @chars'()[]{}<>«»' /*can't contain "empty", ?, blank.*/ |
|||
call display |
|||
return |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
mark: parse arg xx,yy,pointChar /*place marker, check for errors. */ |
|||
if pointChar=='' then pointChar= word( substr(@chars, turn, 1) "+", 1) |
|||
xxcyy= xx','yy; _.1= xx; _.2= yy |
|||
do j=1 for 2; XorY= substr('XY', j, 1) /*make sure X and Y are integers. */ |
|||
t: say arg(1); call lineout oFID,arg(1); return |
|||
if _.j=='' then do; call err XorY "wasn't specified." ;return 0; end |
|||
Gshot: Gshots=Gshots arg(1)','arg(2); return |
|||
if \isNum(_.j) then do; call err XorY "isn't numeric:" _.j ; return 0; end |
|||
tranGC: if gC=='' then return arg(1); return translate(arg(1),copies(gC,12),'┌┐└┘│─╔╗╚╝║═') |
|||
if \isInt(_.j) then do; call err XorY "isn't an integer:" _.j; return 0; end |
|||
/*─────────────────────────────────────GREEKCROSS subroutine────────────*/ |
|||
end /*j*/ |
|||
GreekCross: wins=0; loX=-1; hiX=0; LB=gS-1 /*Low Bar*/ |
|||
lintel=LB-2; turn=1; loY=-1; hiY=0; ht=4+3*(LB-2) /*─ ─ */ |
|||
Gshots=; nook=gS-2; Hnook=ht-nook+1; TB=ht-LB+1 /*Top Bar*/ |
|||
/*─ ─ */ |
|||
do y=1 for ht; _top='╔'copies('═',lintel)'╗' ; _top=tranGC(_top) |
|||
_bot='╚'copies('═',lintel)'╝' ; _bot=tranGC(_bot) |
|||
_hib='╔'copies('═',lintel)'╝'left('',lintel)'╚'copies('═',lintel)'╗' ; _hib=tranGC(_hib) |
|||
_lob='╚'copies('═',lintel)'╗'left('',lintel)'╔'copies('═',lintel)'╝' ; _lob=tranGC(_lob) |
|||
_sid='║' ; _sid=tranGC(_sid) |
|||
select |
|||
when y==1 then do x=1 for LB; call place x+LB-1,y,substr(_bot,x,1); end |
|||
when y==ht then do x=1 for LB; call place x+LB-1,y,substr(_top,x,1); end |
|||
when y==LB then do x=1 for ht; if x>LB & x<TB then iterate; call place x,y,substr(_lob,x,1); end |
|||
when y==TB then do x=1 for ht; if x>LB & x<TB then iterate; call place x,y,substr(_hib,x,1); end |
|||
when y>LB & y<TB then do x=1 by ht-1 for 2; call place x,y,_sid; end |
|||
otherwise do x=LB by TB-LB for 2; call place x,y,_sid; end |
|||
end /*select*/ |
|||
end /*y*/ |
|||
xx= xx / 1; yy= yy / 1 /*normalize integers: + 7 or 5.0*/ |
|||
@abc='abcdefghijklmnopqrstuvwxyz'; @chars='0123456789'translate(@abc)||@abc |
|||
if pointChar==empty |, |
|||
@chars=@chars'()[]{}<>«»' /*can't contain "empty", ?, blank*/ |
|||
pointChar=='?' then do; call err 'illegal point character:' pointChar; return 0 |
|||
end |
|||
if @.xx.yy\==empty then do; call err 'point' xxcyy "is already occupied."; return 0 |
|||
end |
|||
if \neighbor(xx,yy) then do; call err "point" xxcyy "is a bad move." ; return 0 |
|||
end |
|||
call place xx,yy,'?' |
|||
newWins= seeIfWin() |
|||
if newWins==0 then do; call err 'point' xxcyy "isn't a good move." |
|||
@.xx.yy= empty; return 0 |
|||
end |
|||
call t "move" turn ' ('xx","yy') with "'pointChar'"' |
|||
wins= wins + newWins; @.xx.yy= pointChar |
|||
call display; turn= turn + 1 |
|||
return 1 |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
neighbor: parse arg a,b; am= a - 1; ap= a + 1; bm= b - 1; bp= b + 1 |
|||
return @.am.b\==empty | @.am.bm\==empty | @.ap.b\==empty | @.am.bp \== empty |, |
|||
@.a.bm\==empty | @.ap.bm\==empty | @.a.bp\==empty | @.ap.bp\==empty |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
noValue: syntax: prompt=; quiet= 0 |
|||
call err 'REXX program' condition('C') "error", condition('D'), , |
|||
"REXX source statement (line" sigl"):", sourceline(sigl) |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
place: parse arg xxp,yyp /*place a marker (point) on grid.*/ |
|||
loX= min(loX, xxp); hiX= max(hiX, xxp) |
|||
loY= min(loY, yyp); hiY= max(hiY, yyp); @.xxp.yyp= arg(3) |
|||
return |
|||
/*──────────────────────────────────────────────────────────────────────────────────────*/ |
|||
seeIfWin: y=yy; z= @.xx.yy /*count horizontal/vertical/diagonal wins.*/ |
|||
do x=xx+1; if @.x.y==empty then leave; z= z||@.x.y; end |
|||
do x=xx-1 by -1; if @.x.y==empty then leave; z= @.x.y||z; end |
|||
if ?win(z) then return 1 /*────────count wins in horizontal line. */ |
|||
x= xx; z= @.xx.yy |
|||
do y=yy+1; if @.x.y==empty then leave; z= z||@.x.y; end |
|||
do y=yy-1 by -1; if @.x.y==empty then leave; z= @.x.y||z; end |
|||
if ?win(z) then return 1 /*────────count wins in vertical line. */ |
|||
x= xx; z= @.xx.yy |
|||
do y=yy+1; x= x + 1; if @.x.y==empty then leave; z= z||@.x.y; end |
|||
x= xx |
|||
do y=yy-1 by -1; x=x-1; if @.x.y==empty then leave; z= @.x.y||z; end |
|||
if ?win(z) then return 1 /*──────count diag wins: up & >, down & < */ |
|||
x= xx; z= @.xx.yy |
|||
do y=yy+1; x= x - 1; if @.x.y==empty then leave; z= z||@.x.y; end |
|||
x= xx |
|||
do y=yy-1 by -1; x=x+1; if @.x.y==empty then leave; z= z||@.x.y; end |
|||
return ?win(z) /*──────count diag wins: up & <, down & > */</lang> |
|||
This REXX program makes use of '''LINESIZE''' REXX program (or BIF) which is used to determine the screen width (or linesize) of the terminal (console). |
|||
<br>The '''LINESIZE.REX''' REXX program is included here ──► [[LINESIZE.REX]].<br> |
|||
{{out|output|text= when running 1,500 trials, the highest win was a meager 47 (four games, all different), and one of them is shown below.}} |
|||
call display |
|||
<pre> |
|||
call Gshot nook , nook ; call Gshot nook , Hnook |
|||
···☼☼☼☼··· |
|||
call Gshot Hnook , nook ; call Gshot Hnook , Hnook |
|||
···☼··☼··· |
|||
···☼··☼··· |
|||
☼☼☼☼··☼☼☼☼ |
|||
☼········☼ |
|||
☼········☼ |
|||
☼☼☼☼··☼☼☼☼ |
|||
···☼··☼··· |
|||
return |
|||
···☼··☼··· |
|||
/*─────────────────────────────────────DISPLAY subroutine───────────────*/ |
|||
···☼☼☼☼··· |
|||
display: call t; do y=hiY to loY by -1; _=indent /*start at a high Y.*/ |
|||
═══════════════════════════════════════════════════════════════════════════════ |
|||
do x=loX to hiX /*build an "X" line.*/ |
|||
!=@.x.y; xo=x==0; yo=y==0 |
|||
if !==empty then do /*grid transformation*/ |
|||
if xo then !='|' |
|||
if xo & y//5 ==0 then !='├' |
|||
if xo & y//10==0 then !='╞' |
|||
if yo then !='─' |
|||
if yo & x//5 ==0 then !='┴' |
|||
if yo & x//10==0 then !='╨' |
|||
if xo & yo then !='┼' |
|||
end |
|||
_=_ || ! |
|||
end /*x*/ |
|||
call t _ /*...and display it.*/ |
|||
end /*y*/ |
|||
move 1 (11,4) with "1" |
|||
if wins==0 then call t copies('═',sw) |
|||
else call t right('count of (above) wins =' wins,sw,'═') |
|||
call t |
|||
return |
|||
/*─────────────────────────────────────PLACE subroutine─────────────────*/ |
|||
place: parse arg xxp,yyp /*place a marker (point) on grid.*/ |
|||
loX=min(loX,xxp); hiX=max(hiX,xxp) |
|||
loY=min(loY,yyp); hiY=max(hiY,yyp); @.xxp.yyp=arg(3) |
|||
return |
|||
/*─────────────────────────────────────MARK subroutine──────────────────*/ |
|||
mark: parse arg xx,yy,pointChar /*place marker, check for errors.*/ |
|||
if pointChar=='' then pointChar=word(substr(@chars,turn,1) '+',1) |
|||
xxcyy=xx','yy; _.1=xx; _.2=yy |
|||
··········· |
|||
do j=1 for 2; XorY=substr('XY',j,1) /*make sure X and Y are integers.*/ |
|||
···☼☼☼☼···· |
|||
···☼··☼···· |
|||
if \datatype(_.j,'N') then do; call err XorY "isn't numeric:" _.j ; return 0; end |
|||
···☼··☼···· |
|||
if \datatype(_.j,'W') then do; call err XorY "isn't an integer:" _.j; return 0; end |
|||
☼☼☼☼··☼☼☼☼· |
|||
end |
|||
☼········☼· |
|||
☼········☼· |
|||
☼☼☼☼··☼☼☼☼1 |
|||
···☼··☼···· |
|||
···☼··☼···· |
|||
···☼☼☼☼···· |
|||
═══════════════════════════════════════════════(above) the board after 1 turns. |
|||
move 2 (4,5) with "2" |
|||
xx=xx/1; yy=yy/1 /*normalize integers: + 7 or 5.0*/ |
|||
··········· |
|||
if pointChar==empty |, |
|||
···☼☼☼☼···· |
|||
pointChar=='?' then do; call err 'illegal point character:' pointChar; return 0; end |
|||
···☼··☼···· |
|||
if @.xx.yy\==empty then do; call err 'point' xxcyy 'is already occupied.'; return 0; end |
|||
···☼··☼···· |
|||
if \neighbor(xx,yy) then do; call err "point" xxcyy "is a bad move." ; return 0; end |
|||
☼☼☼☼··☼☼☼☼· |
|||
call place xx,yy,'?' |
|||
☼········☼· |
|||
newWins=countWins() |
|||
☼··2·····☼· |
|||
if newWins==0 then do; call err "point" xxcyy "isn't a good move." |
|||
☼☼☼☼··☼☼☼☼1 |
|||
···☼··☼···· |
|||
···☼··☼···· |
|||
···☼☼☼☼···· |
|||
call t "move" turn ' ('xx","yy') with "'pointChar'"' |
|||
═══════════════════════════════════════════════(above) the board after 2 turns. |
|||
wins=wins+newWins; @.xx.yy=pointChar; call display; turn=turn+1 |
|||
return 1 |
|||
/*─────────────────────────────────────NEIGHBOR subroutine──────────────*/ |
|||
neighbor: parse arg a,b; am=a-1; ap=a+1 |
|||
bm=b-1; bp=b+1 |
|||
return @.am.b \== empty | @.am.bm \== empty |, |
|||
@.ap.b \== empty | @.am.bp \== empty |, |
|||
@.a.bm \== empty | @.ap.bm \== empty |, |
|||
@.a.bp \== empty | @.ap.bp \== empty |
|||
/*─────────────────────────────────────COUNTALINE subroutine────────────*/ |
|||
countAline: arg z ; L=length(z) |
|||
if L>gS then do; if gT=='D' then return 0 /*longlines ¬ kosker for D*/ |
|||
parse var z z1 '?' z2 /*could be xxxxx?xxxx */ |
|||
return length(z1)==4 | length(z2)==4 |
|||
end |
|||
return L==gS |
|||
/*─────────────────────────────────────COUNTWINS subroutine─────────────*/ |
|||
countWins: eureka=0; y=yy /*count horizontal/vertical/diagonal wins.*/ |
|||
z=@.xx.yy |
|||
do x=xx+1; if @.x.y==empty then leave; z=z||@.x.y; end |
|||
do x=xx-1 by -1; if @.x.y==empty then leave; z=@.x.y||z; end |
|||
eureka=eureka+countAline(z) /*─────────count wins in horizontal line. */ |
|||
x=xx |
|||
z=@.xx.yy |
|||
do y=yy+1; if @.x.y==empty then leave; z=z||@.x.y; end |
|||
do y=yy-1 by -1; if @.x.y==empty then leave; z=@.x.y||z; end |
|||
eureka=eureka+countAline(z) /*─────────count wins in vertical line. */ |
|||
x=xx |
|||
z=@.xx.yy |
|||
do y=yy+1; x=x+1; if @.x.y==empty then leave; z=z||@.x.y; end |
|||
x=xx |
|||
do y=yy-1 by -1; x=x-1; if @.x.y==empty then leave; z=@.x.y||z; end |
|||
eureka=eureka+countAline(z) /*───────count diag wins: up&>, down&< */ |
|||
x=xx |
|||
z=@.xx.yy |
|||
do y=yy+1; x=x-1; if @.x.y==empty then leave; z=z||@.x.y; end |
|||
x=xx |
|||
do y=yy-1 by -1; x=x+1; if @.x.y==empty then leave; z=z||@.x.y; end |
|||
return eureka+countAline(z) /*───────count diag wins: up&<, down&> */</lang> |
|||
This REXX program makes use of '''LINESIZE''' REXX program (or BIF) which is used to determine the screen width (or linesize) of the terminal (console). |
|||
<br>The '''LINESIZE.REX''' REXX program is included here ──► [[LINESIZE.REX]].<br> |
|||
'''output''' when running 1,500 trials, the highest win was a meager 44 (four games, all different), and |
|||
one of them is shown below. |
|||
<pre style="height:100ex"> |
|||
·╞···╔══╗··· |
|||
·|···║··║··· |
|||
·|···║··║··· |
|||
·|╔══╝··╚══╗ |
|||
·|║········║ |
|||
·├║········║ |
|||
·|╚══╗··╔══╝ |
|||
·|···║··║··· |
|||
·|···║··║··· |
|||
·|···╚══╝··· |
|||
─┼────┴────╨ |
|||
·|·········· |
|||
═══════════════════════════════════════════════════════════════════════════════ |
|||
move 1 (3,3) with "0" |
|||
... previous 46 moves elided ... above is the initial board (grid) ... |
... previous 46 moves elided ... above is the initial board (grid) ... |
||
--- the next line means: 47th move, position=9,9 marked with an "k" --- |
--- the next line means: 47th move, position=9,9 marked with an "k" --- |
||
move 47 (9,9) with "k" |
move 47 (9,9) with "k" |
||
···iQagP···· |
|||
· |
·j·d☼☼☼☼F··· |
||
··hO☼NL☼ck·· |
|||
· |
·CZ1☼bK☼3MD· |
||
X☼☼☼☼57☼☼☼☼f |
|||
· |
·☼YHASGBJR☼· |
||
· |
·☼UT8I·9·e☼· |
||
· |
·☼☼☼☼46☼☼☼☼· |
||
· |
V··0☼W·☼2··· |
||
· |
····☼··☼···· |
||
· |
····☼☼☼☼E··· |
||
─┼────┴────╨── |
|||
·|············ |
|||
═════════════════════════════════════════════════════ count of (above) wins = 47 |
═════════════════════════════════════════════════════ count of (above) wins = 47 |