« 携帯から |Main| 日記 »

« Pythonのジェネレータを使ってprivateな変数 | Python | Re: Re: Pythonのジェネレータで四角いらせんを書いた »

Pythonのジェネレータで四角いらせんを書いた

Javaで書く必要があったのですが。
>>> def squareSpiral():
	width = 0
	(x, y) = (0, 0)
	yield (x, y)
	while True:
		width += 1
		for i in range(width):
			x += 1
			yield (x, y)
		for i in range(width):
			y += 1
			yield (x, y)
		width += 1
		for i in range(width):
			x -= 1
			yield (x, y)
		for i in range(width):
			y -= 1
			yield (x, y)

			
>>> g = squareSpiral()
>>> for i in range(10):
	print g.next()

	
(0, 0)
(1, 0)
(1, 1)
(0, 1)
(-1, 1)
(-1, 0)
(-1, -1)
(0, -1)
(1, -1)
(2, -1)
とこんな風にアルゴリズムが正しく動いていることを確認してからJavaで書く。 Javaっでこのアルゴリズムを実装しようとすると、 「ループの中でフラグを立てておいてループの外でそのフラグをチェックしてさらにbreakする」とか「上のコードでどのループの中にいるのかに相当する変数を持っておいて、それに応じてnextが呼ばれたときの挙動を変える」とかが必要なのだけど、 いきなりそういうごちゃごちゃしたのを書くとエンバグ率が高い。

だから仕事では100%Javaを使うという人にも、Pythonを学ぶメリットはあるのです。 なんて当たり前すぎる結論かな。


__ で、上のコードを眺めながらJavaで書いてみました。

private void init(){
	phase = 0;
}

private void next(){
	if(phase == 0){
		x = 0;
		y = 0;
		phase = 1;
		width = 1;
		i = 0;
	}else if(phase == 1){
		x += 1;
		i += 1;
		if(i == width){
			phase = 2;
			i = 0;
		}
	}else if(phase == 2){
		y += 1;
		i += 1;
		if(i == width){
			phase = 3;
			width += 1;
			i = 0;
		}
	}else if(phase == 3){
		x -= 1;
		i += 1;
		if(i == width){
			phase = 4;
			i = 0;
		}
	}else if(phase == 4){
		y -= 1;
		i += 1;
		if(i == width){
			phase = 1;
			i = 0;
			width += 1;
		}
	}
}

public static void main(String[] args) {
	// test
	SeparateComponentLayout s = new SeparateComponentLayout();
	s.init();
	for(int i = 0; i < 10; i++){
		s.next();
		System.out.println(s.x + ", " + s.y);
	}
}

結果がPythonと同じになることを確認。めでたしめでたし。どちらも一発OKだったので非常に楽でした。最初からJavaで書いたらこうはいかなかったかと思います。

トラックバック(Trackback)

Trackback URL: http://www.nishiohirokazu.org/mt/mt-tb.cgi/407

ご意見・ご感想をお送りください(フィードバック)

(フィードバックはメールで送信され、基本的に表示されませんが、内容によっては公開させていただくこともございます。ご了承ください。Your comment doesn't appear the page immediately. If the comment has value to other people, it will be put on the page or subsequent entries. Thank you.)

上の情報は、いずれも未記入でかまいません。 All of above questions are optional.