🐣

RubyでFizzBuzz問題を解いてみよう

2023/03/27に公開2

使用したバージョン: Ruby 3.1.3

FizzBuzz問題の仕様:

  • 1〜100までの数字をターミナルに出力する
  • 3の倍数のときは「Fizz」
  • 5の倍数のときは「Buzz」
  • 3と5の倍数である「15の倍数」のときは「FizzBuzz」と出力する
  • これら以外のときは数字を返す

今回書いたコード。

def run_fizzbuzz
  (1..100).each do |num|
    puts fizzbuzz(num)
  end
end

def fizzbuzz(num)
  if (num % 15).zero?
    'FizzBuzz'
  elsif (num % 5).zero?
    'Buzz'
  elsif (num % 3).zero?
    'Fizz'
  else
    num
  end
end

if num % 15 == 0と書くのが一般的だと思うけど、せっかくRubyを使っているのでNumeric#zero?を使ってみた。
Numeric#zero? (Ruby 3.2 リファレンスマニュアル)

ついでにminitestでテストも書いてみる。(本当は条件で分けたほうがいいのだけど1つのケースにまとめちゃう)

require 'minitest/autorun'
require 'minitest/reporters'
Minitest::Reporters.use!

class TestFizzBuzz < Minitest::Test
  def test_fizzbuzz
    assert_equal 'FizzBuzz', fizzbuzz(15)
    assert_equal 'FizzBuzz', fizzbuzz(30)
    assert_equal 'Buzz', fizzbuzz(5)
    assert_equal 'Buzz', fizzbuzz(10)
    assert_equal 'Fizz', fizzbuzz(3)
    assert_equal 'Fizz', fizzbuzz(6)
    assert_equal 7, fizzbuzz(7)
    assert_equal 14, fizzbuzz(14)
  end
end

ちなみに、ChatGPT神に解いてもらうとこんな感じ。

(1..100).each do |num|
  if num % 3 == 0 && num % 5 == 0
    puts "FizzBuzz"
  elsif num % 3 == 0
    puts "Fizz"
  elsif num % 5 == 0
    puts "Buzz"
  else
    puts num
  end
end

すばらしいほどに模範的🤖

ちなみにGPTにテストも書いてもらったら、これまた模範的で素晴らしい。てかすごいな・・・。

require 'minitest/autorun'

def fizzbuzz(num)
  if num % 3 == 0 && num % 5 == 0
    "FizzBuzz"
  elsif num % 3 == 0
    "Fizz"
  elsif num % 5 == 0
    "Buzz"
  else
    num
  end
end

class FizzBuzzTest < Minitest::Test
  def test_returns_fizz_when_the_number_is_divisible_by_3
    assert_equal 'Fizz', fizzbuzz(3)
    assert_equal 'Fizz', fizzbuzz(9)
  end

  def test_returns_buzz_when_the_number_is_divisible_by_5
    assert_equal 'Buzz', fizzbuzz(5)
    assert_equal 'Buzz', fizzbuzz(10)
  end

  def test_returns_fizzbuzz_when_the_number_is_divisible_by_both_3_and_5
    assert_equal 'FizzBuzz', fizzbuzz(15)
    assert_equal 'FizzBuzz', fizzbuzz(30)
  end

  def test_returns_the_number_itself_when_the_number_is_not_divisible_by_3_or_5
    assert_equal 1, fizzbuzz(1)
    assert_equal 7, fizzbuzz(7)
  end
end

久々にFizzBuzz問題を解いてみたら、思ったより良い気分転換になった。素のRubyを触るのはやっぱり楽しい。プログラミングの楽しさを思い出せた気がする🕺

Discussion

Junichi ItoJunichi Ito

zero?を使うならmoduloも使って演算子をなくしてしまうのもいいかも?

def fizzbuzz(num)
  if num.modulo(15).zero?
    'FizzBuzz'
  elsif num.modulo(5).zero?
    'Buzz'
  elsif num.modulo(3).zero?
    'Fizz'
  else
    num
  end
end
KotaKota

なんと、moduloを知りませんでした!こんな書き方ができたんですね📝
ありがとうございます☺️