世界のナベアツ版FizzBuzz問題

今日の笑いのレッドカーペットでFizzBuzz問題とそっくりなネタを「世界のナベアツ」がやっていたので、それでFizzBuzzを解いてみた。id:t-wadaさんの「デベロッパーテスティング・ライブ」で見たJUnit4.4も使ってみました。

Wikipedia:世界のナベアツ

世界のナベアツFizzBuzz問題のルール」

3の倍数と3のつく数字であほになって、5の倍数で犬になる。

追記:
id:t-wadaさんのコメントを受けてテストを修正しました。
以前のassertEqualsに慣れていると、うっかり間違えちゃいますね。JUnit4.4流の書き方でしばらく書いてみて慣れていってみようと思います。

assertThatでは、(英語として読めるように意図しているため)期待値と実際値の順番が逆になります。
ですから、
assertThat(”1”, is(fizzBuzz.fizzBuzz(1)));
ではなくて
assertThat(fizzBuzz.fizzBuzz(1), is(”1”));


FizzBuzzTest.java

package jp.co.nulab.sekainonabeatsu;

import java.io.StringWriter;

import junit.framework.TestCase;

import org.junit.Test;

import static org.junit.Assert.assertThat;

import static org.hamcrest.core.Is.is;

public class FizzBuzzTest extends TestCase {

	@Test
	public void testFuzzBuzz() {
		FizzBuzz fizzBuzz = new FizzBuzz(new StringWriter());
		assertThat(fizzBuzz.fizzBuzz(1), is("1"));
		assertThat(fizzBuzz.fizzBuzz(2), is("2"));
		assertThat(fizzBuzz.fizzBuzz(3), is("3( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(4), is("4"));
		assertThat(fizzBuzz.fizzBuzz(5), is("5U^ェ^U"));
		assertThat(fizzBuzz.fizzBuzz(6), is("6( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(7), is("7"));
		assertThat(fizzBuzz.fizzBuzz(8), is("8"));
		assertThat(fizzBuzz.fizzBuzz(9), is("9( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(10), is("10U^ェ^U"));

		assertThat(fizzBuzz.fizzBuzz(11), is("11"));
		assertThat(fizzBuzz.fizzBuzz(12), is("12( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(13), is("13( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(14), is("14"));
		assertThat(fizzBuzz.fizzBuzz(15), is("15( ̄o ̄)ア( ̄O ̄)ホッ!U^ェ^U"));
		assertThat(fizzBuzz.fizzBuzz(16), is("16"));
		assertThat(fizzBuzz.fizzBuzz(17), is("17"));
		assertThat(fizzBuzz.fizzBuzz(18), is("18( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(19), is("19"));
		assertThat(fizzBuzz.fizzBuzz(20), is("20U^ェ^U"));

		assertThat(fizzBuzz.fizzBuzz(21), is("21( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(22), is("22"));
		assertThat(fizzBuzz.fizzBuzz(23), is("23( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(24), is("24( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(25), is("25U^ェ^U"));
		assertThat(fizzBuzz.fizzBuzz(26), is("26"));
		assertThat(fizzBuzz.fizzBuzz(27), is("27( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(28), is("28"));
		assertThat(fizzBuzz.fizzBuzz(29), is("29"));
		assertThat(fizzBuzz.fizzBuzz(30), is("30( ̄o ̄)ア( ̄O ̄)ホッ!U^ェ^U"));

		assertThat(fizzBuzz.fizzBuzz(31), is("31( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(32), is("32( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(33), is("33( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(34), is("34( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(35), is("35( ̄o ̄)ア( ̄O ̄)ホッ!U^ェ^U"));
		assertThat(fizzBuzz.fizzBuzz(36), is("36( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(37), is("37( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(38), is("38( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(39), is("39( ̄o ̄)ア( ̄O ̄)ホッ!"));
		assertThat(fizzBuzz.fizzBuzz(40), is("40U^ェ^U"));
	}

	@Test
	public void 全パターンの出力() {
		// 標準出力の場合 new OutputStreamWriter(System.out);
		StringWriter out = new StringWriter();
		FizzBuzz fizzBuzz = new FizzBuzz(out);
		fizzBuzz.fizzBuzzAll();
		String expected = "1\n2\n3( ̄o ̄)ア( ̄O ̄)ホッ!\n4\n5U^ェ^U\n6( ̄o ̄)ア( ̄O ̄)ホッ!\n7\n8\n9( ̄o ̄)ア( ̄O ̄)ホッ!\n10U^ェ^U\n11\n" +
				"12( ̄o ̄)ア( ̄O ̄)ホッ!\n13( ̄o ̄)ア( ̄O ̄)ホッ!\n14\n15( ̄o ̄)ア( ̄O ̄)ホッ!U^ェ^U\n16\n17\n18( ̄o ̄)ア( ̄O ̄)ホッ!\n19\n20U^ェ^U\n" +
				"21( ̄o ̄)ア( ̄O ̄)ホッ!\n22\n23( ̄o ̄)ア( ̄O ̄)ホッ!\n24( ̄o ̄)ア( ̄O ̄)ホッ!\n25U^ェ^U\n26\n27( ̄o ̄)ア( ̄O ̄)ホッ!\n28\n29\n30( ̄o ̄)ア( ̄O ̄)ホッ!U^ェ^U\n" +
				"31( ̄o ̄)ア( ̄O ̄)ホッ!\n32( ̄o ̄)ア( ̄O ̄)ホッ!\n33( ̄o ̄)ア( ̄O ̄)ホッ!\n34( ̄o ̄)ア( ̄O ̄)ホッ!\n35( ̄o ̄)ア( ̄O ̄)ホッ!U^ェ^U\n36( ̄o ̄)ア( ̄O ̄)ホッ!\n37( ̄o ̄)ア( ̄O ̄)ホッ!\n38( ̄o ̄)ア( ̄O ̄)ホッ!\n39( ̄o ̄)ア( ̄O ̄)ホッ!\n40U^ェ^U\n";
		assertThat(out.toString(), is(expected));
	}
}


FizzBuzz.java

package jp.co.nulab.sekainonabeatsu;

import java.io.IOException;
import java.io.Writer;


public class FizzBuzz {

	private final Writer out;

	public FizzBuzz(Writer out) {
		this.out = out;
	}

	public String fizzBuzz(int no) {
		String noStr = String.valueOf(no);
		StringBuilder sb = new StringBuilder();
		sb.append(noStr);
		if (no % 3 == 0 || noStr.contains("3")) {
			sb.append("( ̄o ̄)ア( ̄O ̄)ホッ!");
		}
		if (no % 5 == 0) {
			sb.append("U^ェ^U");
		}
		return sb.toString();
	}

	public void fizzBuzzAll() {
		for (int i = 1; i < 41; i++) {
			try {
				this.out.append(fizzBuzz(i));
				this.out.append("\n");
			} catch (IOException e) {
				throw new RuntimeException(e);
			}
		}
	}
}