あみだくじを作ってみよう4

 

パソコンというかコンピュータは堅物ですから、
ほとんどの場合は、毎回同じ反応をします。

毎度、管理人イガジーです。

時には違う反応をさせたい場合(や、ゲームなどで)は
乱数を使って、違う結果を出すようにするのですが
そういうプログラムがバグってしまうと、原因究明がとっても
大変だったりします。

今回は、バグに苦しんだ訳ではありませんが、アミダの
生成ロジックを変更した例(昨日の宿題の解答例)を示しておきます。

/* 昨日のあみだ生成ロジック
for (int n=0;n<(nn*(vn+1));++n) { // 乱数で横棒をセット
	int r=rnd.nextInt(nn*vn);
	int rx=r/vn;
	int ry=r%vn;
	hb[rx][ry]=true;
}
↓↓↓ */
// 縦に見て最低1本は横棒が入るように改善
for (int i=0;i<(nn-1);++i) {  // 乱数で横棒をセット
	for (int j=0;j<(vn-2);++j) {
		int r=rnd.nextInt(vn);
		hb[i][r]=true;
	}
}

(vn-2)に深い意味はありません。vn とすると
ちょっと横棒が多くなりすぎる気がしたので減らしています。

さて、あみだを生成したら、次はあみだを「たどる」処理です。
横棒の有無(hb[][])を見ていくわけですが、
amida-horizonbar
のように、hb[奇数][]は、少し下にずらしているので、
先にhb[偶数][]をチェックして、次にhb[奇数][]を見る必要があります。
(hb[偶数][] を「上段」、hb[奇数][]を「下段」と呼ぶことにします。)

また、左から0から数えて偶数番目の棒は、
上段では「右」(hb[i][])を見て、下段では「左」(hb[i-1][])を見ます。
奇数番目の棒は、上段では「左」を見て、下段では「右」を見ます。
コードにすると

void trace(int k) {
	int y2,x;
	int i=k;
	if (i>nn) i=nn;
	y2=x=0;
	g.setColor(Color.CYAN);
	int yt=y0;
	for (int j=0;j<(vn*2);++j) {
		y2=j*yh2+y0+yh2;
		x=i*xlen+x0;
		g.drawLine(x-1, yt, x-1, y2);
		g.drawLine(x+1, yt, x+1, y2);
		yt=y2;
		if ((i&1)==0) { // 偶数(A,C,E,...)なら
			if ((j&1)==0) { // 上段(ずらしていない方)
//				if (i<(nn-1)){
					if (hb[i][j/2]) { // 右に横棒あり?
						g.drawLine(x, yt-1, x+xlen, yt-1);
						g.drawLine(x, yt+1, x+xlen, yt+1);
						++i;
					}
//				}
			}else{ // 下段(ずらしている方)
				if (i>0) {
					if (hb[i-1][j/2]) { // 左に棒あり?
						g.drawLine(x-xlen, yt-1, x, yt-1);
						g.drawLine(x-xlen, yt+1, x, yt+1);
						--i;
					}
				}
			}
		}else{ // 奇数(B,D,F,...)なら
			if ((j&1)==0) { // 上段
				if (i>0) { // 左端でなければ左を見る
					if (hb[i-1][j/2]) { // 左に棒あり?
						g.drawLine(x-xlen, yt-1, x, yt-1);
						g.drawLine(x-xlen, yt+1, x, yt+1);
						--i;
					}
				}
			}else{ // 下段なら右を見る
//				if (i<(nn-1)) {
					if (hb[i][j/2]) { // 右に棒あり?
						g.drawLine(x, yt-1, x+xlen, yt-1);
						g.drawLine(x, yt+1, x+xlen, yt+1);
						++i;
					}
//				}
			}
		}// endif 奇数の棒
	}// for j
	g.setColor(Color.CYAN);
	x=i*xlen+x0;
	g.drawLine(x-1,yt,x-1,y1);
	g.drawLine(x+1,yt,x+1,y1);
}

という感じになります。
メソッドの引数 k は、何番目の棒をたどるかの指定です。
左端(0)は、チェックしないと hb[i-1][] の参照で例外が置きますが
右端は、hb[][]に余裕持たせておくとチェック無しにもできます。
(上記コードでは、行頭 // でコメントにしています)

動作確認用には、k を指定できるようにしたプログラムを作る必要が
ありますが、それを含めた全コードはまた後日。

この記事へのコメントはこちら

メールアドレスは公開されませんのでご安心ください。
また、* が付いている欄は必須項目となりますので、必ずご記入をお願いします。

内容に問題なければ、下記の「コメント送信」ボタンを押してください。