
With the Asymptote
module permdiag.asy
typesetting
of this nice little permutation game can be completely automated.
Processing of the following file permdiag-test.asy
import permdiag;
permDiag pd=permDiag(new int[]{6,3,2,4,1,5});
for(int i=1;i<=pd.n;++i){
shipout("diag"+format("%02d",i),pd.board(i));
}
with asy -f pdf permdiag-test.asy
results in 6 files diag01.pdf
..diag06.pdf
,
which were combined together with
\documentclass[a4paper]{article}
\usepackage{graphicx}
\begin{document}
\noindent%
\includegraphics[scale=1]{diag00.pdf}\quad
\includegraphics[scale=1]{diag01.pdf}\quad
\includegraphics[scale=1]{diag02.pdf}\\[10mm]
\noindent%
\includegraphics[scale=1]{diag03.pdf}\quad
\includegraphics[scale=1]{diag04.pdf}\quad
\includegraphics[scale=1]{diag05.pdf}
\end{document}
And this is the main permdiag.asy
, which handles the permDiag
class:
struct permDiag{
int n;
int[] perm;
int[] dotState;
int[][] tperm;
picture boardPic;
guide dotShape;
pen[] dotFill;
void drawNumbers(){
for(int i=0;i<n;++i){
label(boardPic,string(i+1),(i,-1));
label(boardPic,string(n-i),(-1,n-1-i));
}
}
void drawArrows(){
for(int i=0;i<n;++i){
if(dotState[i]>0){
if(dotState[i]==1){
label(boardPic,"$\leftarrow$",(n+0.5,tperm[i][0]-1));
}else{
label(boardPic,"$\downarrow$",(tperm[i][2]-1,n+0.5));
}
}
}
}
void drawStars(){
for(int i=0;i<n;++i){
if(dotState[i]>0){
if(dotState[i]==2){
label(boardPic,"*",(-2,tperm[i][0]-1));
}else{
label(boardPic,"*",(tperm[i][3]-1,-2));
}
}
}
}
void drawLines(){
draw(boardPic,(-2.5,-0.5)--(n+1.5,-0.5));
draw(boardPic,(-2.5,n-0.5)--(n+1.5,n-0.5));
draw(boardPic,(-0.5,-2.5)--(-0.5,n+1.5));
draw(boardPic,(n-0.5,-2.5)--(n-0.5,n+1.5));
}
void play(int hstep){
erase(boardPic);
int tmp;
int redblu=0;
for(int i=0;i<n;++i){
tperm[i][0]=perm[i];
tperm[i][4]=i+1;
}
dotState=array(n,0);
for(int i=0;i<hstep;++i){
for(int j=n-1;j>i;--j){
if(tperm[j][redblu]>tperm[j-1][redblu]){
tmp=tperm[j][redblu];
tperm[j][redblu]=tperm[j-1][redblu];
tperm[j-1][redblu]=tmp;
tmp=tperm[j][1-redblu];
tperm[j][1-redblu]=tperm[j-1][1-redblu];
tperm[j-1][1-redblu]=tmp;
}
}
dotState[i]=1+redblu;
redblu=1-redblu;
}
}
picture board(int move){
assert(move>=0 && move<=n);
// move number, 0 = initial state,
// odd - after red move
// even - after blu move
play(move);
for(int i=0;i<n;++i){
filldraw(boardPic,shift(tperm[i][5]-1,tperm[i][0]-1)*dotShape,dotFill[dotState[i]]);
}
drawNumbers();
drawArrows();
drawStars();
drawLines();
label(boardPic,"$\mathcal{S}$",(n+0.5,n+0.5));
return boardPic;
}
void operator init(int[] perm){
assert(perm.length>0);
this.n=perm.length;
this.perm=copy(perm);
this.dotState=array(n,0);
this.dotShape=scale(0.382)*unitcircle;
this.dotFill=new pen[]{lightyellow,red,blue};
this.tperm=new int[n][6];
boardPic.size(20*n);
}
}
//// Example:
//
// import permdiag;
// permDiag pd=permDiag(new int[]{6,3,2,4,1,5});
//
// for(int i=0;i<=pd.n;++i){
// shipout("diag"+format("%02d",i),pd.board(i));
// }
//
Edit: Fixed picture scaling for different values of n
. Example permdiag-test2.asy
:
import permdiag;
permDiag pda=permDiag(new int[]{3,1,2,4});
permDiag pdb=permDiag(new int[]{9,19,17,1,8,13,18,11,10,4,5,7,2,3,15,16,12,6,20,14});
int i;
i=3;
shipout("diag-"+format("n%d-",pda.n)+format("%02d",i),pda.board(i));
i=12;
shipout("diag-"+format("n%d-",pdb.n)+format("%02d",i),pdb.board(i));
processed with asy -f pdf permdiag-test2.asy
results in two pictures,
diag-n4-03.pdf
and diag-n20-12.pdf
:

