Code Fix

中級

case文で該当するwhenが無いとnilが返る

case式はいずれのwhenにも一致しない場合、elseが無ければ例外を出さずnilを返します。switch文がエラーになる言語の感覚のままだと、この静かなnilに気づけません。

なぜエラーが出ないのか

出力: nil
(エラーなし)
Rubyは何も報告しません。文法として正しいためです
出力: nil
実際の挙動 — 期待した結果と食い違っている箇所
見つけ方
エラーが出ないので、出力を目で確かめるしかありません。この種の誤りが最も発見が遅れます

このエラーが出る典型パターン

パターン1

 1  grade = "F"
 2  label = case grade
 3          when "A" then "excellent"
 4          when "B" then "good"
 5                              
                  ^
 6          end
 7  puts label.inspect
出力: nil

case式はどのwhenにも一致しないと、elseが無ければ例外を出さずnilを返します。

直し方: (空) を when "F" then "fail" にします。

この問題を解いてみる →

広告
広告スロット(未設定)

パターン2

 1  status = "cancelled"
 2  label = case status
 3          when "active" then "still going"
 4          when "done" then "finished"
 5                                         
                       ^
 6          end
 7  puts label.inspect
出力: nil

想定していない入力値が来た場合の分岐を書き忘れると、labelはエラーにならずnilになってしまいます。

直し方: (空) を when "cancelled" then "stopped" にします。

この問題を解いてみる →

パターン3

 1  size = "XL"
 2  label = case size
 3          when "S" then "small"
 4          when "M" then "medium"
 5                                      
                      ^
 6          end
 7  puts label.inspect
出力: nil

switch文がエラーになる言語の感覚のままだと、Rubyのcaseがnilで通り抜けることに気づきにくいです。

直し方: (空) を when "XL" then "extra large" にします。

この問題を解いてみる →

パターン4

 1  day = "Sunday"
 2  label = case day
 3          when "Monday" then "weekday"
 4          when "Saturday" then "weekend"
 5                                      
                      ^
 6          end
 7  puts label.inspect
出力: nil

考慮漏れの値をelseで拾っておかないと、そのケースだけ静かにnilを返す分岐になります。

直し方: (空) を when "Sunday" then "weekend" にします。

この問題を解いてみる →

パターン5

 1  role = "guest"
 2  label = case role
 3          when "admin" then "full access"
 4          when "member" then "limited access"
 5                                       
                      ^
 6          end
 7  puts label.inspect
出力: nil

すべての分岐を網羅したつもりでも、テストで実際に出力を確認しないとnilの通り抜けには気づけません。

直し方: (空) を when "guest" then "read only" にします。

この問題を解いてみる →

よくある誤解

「該当するwhenが無ければ何かエラーになるはず」という思い込みは誤りです。case式は一致が無くてもそのままnilという値を返して処理を続けるため、想定外の入力が静かに無視されます。

実務での勘所

この挙動は、case文だけの特別ルールではなく、Rubyの「制御構造もすべて値を持つ式である」という一貫した設計から来ています。if文もelseが無ければ、条件がfalseのときにnilを返します(if false; "x"; endはnilになります)。case文がelseに相当する分岐が無いときにnilを返すのも、この同じ原則の帰結です。Rubyでは代入や関数の引数としてif・caseの結果をそのまま使えるのも、すべての制御構造が値を返す式として設計されているためです。

演習をはじめる

関連するエラー

広告
広告スロット(未設定)