Javaでプログラムのアルゴリズム問題で有名なFizzBuzzを書いてみます。ノーマルな実装方法と、応用として拡張性を意識した実装方法を紹介します。
FizzBuzzプログラムは、プログラミングを始めたばかりの人に出されることが多いアルゴリズムの問題です。初級者にとってはアルゴリズムの登竜門ですね。
私も、大学の頃C言語の授業で出された記憶があります。プログラミングを勉強している人は知っている人が多いのではないでしょうか。
今回は100まで表示させると出力結果が長くなってしまうので、20まで出力させてみます。
色々と解答方法があるかと思いますが、一番ノーマルな書き方で実装してみます。
1public class FizzBuzzTest1 {
2 public static void main(String[] args) {
3 for (int num = 1; num <= 20; num++) {
4 // 15で割り切れる時FizzBuzzと出力する
5 if (num % 15 == 0) {
6 System.out.println("FizzBuzz");
7 }
8 // 3で割り切れる時Fizzと出力する
9 else if (num % 3 == 0) {
10 System.out.println("Fizz");
11 }
12 // 5で割り切れる時Buzzと出力する
13 else if (num % 5 == 0) {
14 System.out.println("Buzz");
15 }
16 // それ以外はそのまま出力する
17 else {
18 System.out.println(num);
19 }
20 }
21 }
22}
実行結果が以下になります。
11
22
3Fizz
44
5Buzz
6Fizz
77
88
9Fizz
10Buzz
1111
12Fizz
1313
1414
15FizzBuzz
1616
1717
18Fizz
1919
20Buzz
このアルゴリズムではif文
と%演算子
を使って倍数の判定ができるかがポイントになります。その他、注意する点として倍数の判定の順番があります。最初に15の倍数判定をしないと、3もしくは5の倍数判定に通ってしまうため、ルールを満たさない結果が返ってきます。
上記の解答例だとノーマル過ぎて味気がありませんので、応用例としてルールの追加・変更に強いような実装方法を考えてみましょう。
例えば、条件を追加したり異なる条件にしたい時、上のコードではif文を適宜書き換えていけば実現できますが、いちいちif文の条件式を追加変更するのは少し面倒です。
コードの書き換えが簡単になるような実装にしてみます。
1import java.util.Collections;
2import java.util.Map;
3import java.util.TreeMap;
4
5public class FizzBuzzTest2 {
6 public static void main(String[] args) {
7 // 条件(倍数と文字列)の指定
8 Map<Integer, String> fizzbuzzMap = new TreeMap<>(Collections.reverseOrder());
9 fizzbuzzMap.put(3, "fizz");
10 fizzbuzzMap.put(5, "buzz");
11 fizzbuzzMap.put(15, "buzzfizz");
12 // 表示を行う
13 for (int num = 1; num <= 20; num++) {
14 System.out.println(getString(num, fizzbuzzMap));
15 }
16 }
17
18 // 倍数判定を行うメソッド
19 private static String getString(int num, Map<Integer, String> fizzbuzzMap) {
20 String str = String.valueOf(num);
21 for (int key : fizzbuzzMap.keySet()) {
22 if (num % key == 0) {
23 return fizzbuzzMap.get(key);
24 }
25 }
26 return str;
27 }
28}
実行結果が以下になります。
11
22
3Fizz
44
5Buzz
6Fizz
77
88
9Fizz
10Buzz
1111
12Fizz
1313
1414
15FizzBuzz
1616
1717
18Fizz
1919
20Buzz
このコードではgetStringメソッド
で倍数判定を行い、引数のTreeMap
に倍数と表示したい文字列を格納しています。Collections.reverseOrder()
を指定することで、TreeMap
を自動でキーの降順に並び替えられます。ここでキーの降順に並び替えているのは、数字の大きい順に倍数判定を行わないと正しい判定がされないからです(15の判定時に3の倍数判定がされて「Fizz」が戻ってくるなど)。
条件を変えたい時はputメソッド
の所を好きな物に書き換えるだけで良いので、最初のコードよりかはルール変更に強い実装にすることができました。
色々と実装方法はありますので、皆さんも気軽に挑戦してみましょう。以上で記事を終わりにします。