LoginSignup
2
3

More than 5 years have passed since last update.

省略可能な引数でnilが渡されたのかデフォルト値が使われたのか区別するやり方

Last updated at Posted at 2016-06-18

省略可能な引数のデフォルト値にnilを使うと、引数にnilを渡したのかデフォルト値のnilが使われたのか分かりません。
例えば以下のような問題がおきます

class OkinawaSobaRestaurant
  def 沖縄そば(フーチバー: nil)
    if フーチバー
      puts "沖縄そば、フーチーバーは#{フーチバー}"
    else
      puts "沖縄そば、フーチーバーはサービス"
    end
  end
end

すばやー = OkinawaSobaRestaurant.new

# フーチバーの気分じゃないとき、なしにしてほしいのにサービスされてしまう
すばやー.沖縄そば(フーチバー: nil)
# 沖縄そば、フーチーバーはサービス

こういうときはデフォルト値にnilのような一般的な値を使わず、デフォルト値の役割に応じた名前で定数を宣言すると便利です。

class OkinawaSobaRestaurant
  # nilと区別できるよう、デフォルト値用の値を用意しておく
  # 引数で渡される値と被らないようにオブジェクトのインスタンスを作り定数として保持する
  GIVE_FUCHIBA = Object.new
  # だが、このメソッド以外からは使われてほしくないので、privateな定数に変更する
  private_constant :GIVE_FUCHIBA

  # デフォルトではフーチバーをサービスする
  def 沖縄そば(フーチバー: GIVE_FUCHIBA)
    case フーチバー
    when GIVE_FUCHIBA
      puts "沖縄そば、フーチーバーはサービス"
    when nil
      puts "沖縄そば、フーチーバーはなし"
    else
      puts "沖縄そば、フーチーバーは#{フーチバー}"
    end
  end
end

すばやー = OkinawaSobaRestaurant.new

# フーチバーの気分じゃないとき
puts すばやー.沖縄そば(フーチバー: nil)
# 沖縄そば、フーチーバーはなし

# とにかくそばが食べたいとき
puts すばやー.沖縄そば
# 沖縄そば、フーチーバーはサービス

# フーチバー食べるためにそば食べたいとき
puts すばやー.沖縄そば(フーチバー: :山盛り)
# 沖縄そば、フーチーバーは山盛り

デフォルト値とnilを区別できるようになったので、ふーちばーどうでもいい(デフォルト値)、ふーちばーが食べたくない(nil)、ふーちばー食べたいを表現出来るようになりました。べんりですね。

参考

2
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
3