売れ筋メニューを探せ
中段 / 目安 30分
陽葵さんが仕入れ表を広げて、真剣な顔で言いました。「一番売れたメニューを知りたいの。豆もケーキも、多めに仕入れて余らせたら全部うちの損だから。来月の仕入れがかかってるの」。
数を数えるだけの問題に見えます。ところがJavaでは、ここに入門者のほぼ全員が一度落ちる落とし穴があります。師範はそれを知っていて、あえて何も言わずに見ています。踏んでから気付いてください。そのほうが二度と忘れません。
文字列の比較という落とし穴
数値の比較は == で書きます。では文字列も == でよいかというと、これが違います。
Javaの String はオブジェクトです。== はオブジェクト同士では「中身が同じか」ではなく「同じ実体を指しているか」を見ます。ソースコードに直接書いた "珈琲" 同士なら、たまたま同じ実体が使い回されて true になることがあります。ところが、計算や分割で組み立てられた文字列は別の実体になり、中身が同じでも == は false を返します。
「手元では動いたのに本番で数が合わない」という、いちばんたちの悪いバグの正体がこれです。中身を比べたいときは equals を使ってください。
完成条件
bestSeller(String log) というメソッドを public static で定義してください。
log は本日の注文を記録したもので、商品名がカンマ区切りで並んでいます。たとえば 珈琲,抹茶ラテ,珈琲,シフォンケーキ,珈琲 のような形です。
これを商品名ごとに分解し、最も多く注文された商品名だけを返してください。
- 最多が複数ある場合は、
logの中で先に登場したほうを返します logが空文字列のときは注文なしを返します
返すのは商品名そのものです。件数や記号は付けません。
進め方
白紙から書いてください。手が止まったらヒントを開けます。ヒントは3段階で、①方針、②使う構文、③部分解の順に出ます。1つも開けずに通せたら、その問題は自分のものです。
開かずに10分粘って進まないなら、①だけ開けてください。粘る時間そのものには価値がありません。価値があるのは、自分で書いた行が動いた瞬間です。
分割してできた文字列は、ソースに書いた文字列とは別の実体です。ここで == を使うと、どの商品も1件ずつしか数えられません。もし全部の件数が1になったら、それが落とし穴を踏んだ合図です。比較を equals に書き換えてもう一度動かしてみてください。
要件
- bestSeller(String log) を public static で定義すること
- log をカンマで分割して商品名ごとの件数を数えること
- 文字列の比較は == ではなく equals を使うこと
- 最も件数の多い商品名を返すこと
- 最多が複数あるときは log の中で先に登場したほうを返すこと
- log が空文字列のときは「注文なし」を返すこと
入出力例
bestSeller("珈琲,抹茶ラテ,珈琲,シフォンケーキ,珈琲") → "珈琲"
bestSeller("抹茶ラテ,抹茶ラテ,珈琲") → "抹茶ラテ"
bestSeller("珈琲,抹茶ラテ") → "珈琲"
bestSeller("シフォンケーキ") → "シフォンケーキ"
bestSeller("珈琲,抹茶ラテ,抹茶ラテ,珈琲,シフォンケーキ,シフォンケーキ,抹茶ラテ") → "抹茶ラテ"
bestSeller("") → "注文なし"ヒント
前のヒントを開くと次が開きます。開かずに解けると未開封クリアです