三項演算子

生田 陸人
LuaGate エンジニア / 現役エンジニア
編集 LuaGate編集部

三項演算子 とは

Java の三項演算子 条件 ? 真の値 : 偽の値 を使って、if-else を 1 行で書けるようになろう。

三項演算子で 1 行の条件分岐を書く

Java には、if-else をぎゅっと圧縮したような便利な演算子があります。それが 三項演算子 (ternary operator) です。条件 ? 真の値 : 偽の値 という形で書き、3 つの部分 (オペランド) を取るので「三項」と呼ばれます。Java では +- が 2 つの値を取るので「二項演算子」、++ は 1 つだけなので「単項演算子」、そしてこの ? : だけが 3 つの値を取る唯一の演算子です。

三項演算子は世界の多くのプログラミング言語に存在しますが、Java C C++ JavaScript C# などほとんどが 条件 ? 真 : 偽 という同じ書き方を採用しています。一度覚えれば他の言語でもそのまま通用する、コスパの良い知識です。

書く側からすると「if-else の短縮形」というイメージで構いません。ただし三項演算子は単なる省略記法ではなく、式 (expression) として値を返せる という大事な特徴を持っています。これが if 文との一番大きな違いです。

基本の文法

三項演算子の文法は次のとおりです。

Java

型 変数 = 条件 ? 真の値 : 偽の値;

たとえば、点数が 60 点以上なら "合格"、それ以外なら "不合格" を返す処理を書くと、こうなります。

Java

public class Solution { public static String judge(int score) { String result = score >= 60 ? "合格" : "不合格"; return result; } }

もし同じ処理を if-else で書くと、4 行に膨らみます。

Java

public class Solution { public static String judge(int score) { String result; if (score >= 60) { result = "合格"; } else { result = "不合格"; } return result; } }

見比べると、三項演算子のほうが圧倒的にすっきりしていますね。Java のコードは長くなりがちなので、こうした 1 行に収まる短縮表現は読みやすさにつながります。

ただし「短い = 正義」ではありません。三項演算子は 短く書けるシンプルなケース にとくに向いていて、複雑な条件には向きません。後述する「ネスト」の話で、その境界を一緒に確認していきましょう。

動きを追ってみる

三項演算子は、左から順番に評価されていきます。score >= 60 ? "合格" : "不合格" を例にすると、まず score >= 60 という比較が truefalse かを判定します。true なら ? の直後の "合格" が、false なら : の直後の "不合格" が、その式の値になります。

下の図は score = 70 を渡したときの評価の流れです。

diagram (will load when visible)

図のとおり、? の前で分岐し、合流したあとで変数 result に代入されます。これは if-else のフローとまったく同じですが、三項演算子では これ全体が 1 つの式 なので、return の中に直接埋め込むこともできます。

Java

public class Solution { public static String judge(int score) { return score >= 60 ? "合格" : "不合格"; } }

変数 result を経由する必要すらありません。1 行で読み切れます。

式として値を返せる強み

三項演算子の最大の強みは、if 文と違って 式として値を持つ ことです。これが何を意味するかというと、変数の初期化や return の中、メソッド呼び出しの引数の中に、そのまま埋め込めるということです。

Java

int absValue = n >= 0 ? n : -n; String label = score >= 60 ? "合格" : "不合格"; System.out.println(age >= 20 ? "大人" : "未成年");

1 行目のように 絶対値 (absolute value) を求めるのも、三項演算子の定番のパターンです。n >= 0 なら n をそのまま、n < 0 なら -n (符号を反転した値) を返せば、必ず 0 以上の値になります。

数学で |-5| = 5 |7| = 7 |0| = 0 と書くあの記号が「絶対値」です。Java には Math.abs(n) という標準ライブラリも用意されていますが、今回はあえて三項演算子だけで実装してみましょう。仕組みを自分の手で組み立てると、Math.abs の中身もイメージできるようになります。

ネストはできる、でも基本おすすめしない

三項演算子は ネスト (入れ子) もできます。たとえば点数を "A" "B" "C" の 3 段階に分けたいときは、こんな書き方が可能です。

Java

String grade = score >= 80 ? "A" : score >= 60 ? "B" : "C";

たしかに短いのですが、?: がちらほら出てきて、初見だと読み解くのに頭を使います。実務では「2 段階までは三項演算子、3 段階以上は if-elseswitch」というのが一般的な目安です。

三項演算子は 読み手にとっての負荷 とのトレードオフです。書く本人は楽でも、半年後の自分や同僚が読んで一瞬で理解できるか、という観点で選びましょう。1 段なら歓迎、2 段は要相談、3 段以上は赤信号、くらいの温度感がちょうどいいです。

よくある間違い

三項演算子を初めて触ると、ほぼ全員が同じところでつまずきます。代表的な失敗を 3 つ紹介します。

  • ?: の順番を逆にする — 正しいのは 条件 ? 真の値 : 偽の値 の順番です。条件 : 真の値 ? 偽の値 のように書くとコンパイルエラーになります。「クエスチョン (?) が先、コロン (:) が後」と覚えましょう
  • ネストして読めなくするa ? b ? c : d : e ? f : g のような書き方は、構造を理解していてもパッと意味が取れません。3 段以上のネストは避けて if-elseswitch を使う
  • 両辺の型がずれてコンパイルエラー? の後と : の後で型が違う (例: n >= 0 ? "正の数" : -n) と、Java は「結果の型がひとつに決まらない」と怒ります。文字列と数値を混ぜないように、両辺の型を必ず揃えましょう

もうひとつ、よくあるのが「if 文の代わりに void 処理を三項演算子で書こうとする」失敗です。System.out.println(...) のように 値を返さない処理 は、三項演算子の真偽の枝には書けません。三項演算子は 値を返す式 にだけ使う、と覚えておきましょう。

エラーメッセージで not a statementincompatible types と出たら、三項演算子の使い方を見直すサインです。値を捨てているか、両辺の型が合っていないかのどちらかが原因になっていることが多いです。

やってみよう

それでは、いよいよ今回の課題に挑戦しましょう。

  1. メソッド absoluteValue(int n) の中で、三項演算子を使って n の絶対値を返す
  2. n が 0 以上ならそのまま n、負の数なら -n を返す
  3. if 文は使わない (三項演算子だけで書き切る)

ひな型は次のような形になります。

Java

public class Solution { public static int absoluteValue(int n) { return n >= 0 ? n : -n; } }

n >= 0 という比較を条件にして、? の後ろに「正のときの値」、: の後ろに「負のときの値」を書きます。-nn の符号を反転させる演算で、n = -5 なら -(-5) = 5 になります。これで、どんな整数が渡されても 0 以上の値が返るはずです。

書けたら、テストを実行して absoluteValue(-5)5absoluteValue(7)7absoluteValue(0)0 になることを確認してみましょう。3 件すべて緑になれば合格です。三項演算子の感覚は、こうした小さなお題を何度か書いて手で覚えるのが一番の近道ですよ。

よくある質問

Q. 三項演算子はいつ使うべきですか?

A. 値を 1 行で決めたいときに有効です。たとえば String label = age >= 20 ? "成人" : "未成年"; のような短い条件分岐は読みやすくなります。ネストすると一気に読みにくくなるので、条件が 3 つ以上に増えたら if-else if-else に切り替えましょう。

Q. if 文と三項演算子はどっちが速いですか?

A. 実行速度はほぼ同じです。三項演算子は式(値を返す)、if 文は文(処理を行う)という違いだけです。可読性で選び、副作用のある処理(print、API 呼び出し)は if 文側に書き、純粋な値の選択だけ三項にするのが綺麗です。

Q. 三項演算子で複数の条件を扱えますか?

A. a if cond1 else (b if cond2 else c) と書けますが読みにくくなりがちです。3 段以上は match 文や辞書ルックアップ(grade_label[score])に置き換えた方が拡張も楽です。条件が増えるたびに括弧が増えてレビューで指摘されることが多いポイントです。

次のレッスン

次は じゃんけんの勝敗判定 で、Java の三項演算子 条件 ? 真の値 : 偽の値 を使って、if-else を 1 行で書けるようになろう を学びます。

事前確認 — 進む前に次の 3 つができることを確認しましょう。

  1. 三項演算子 の要点を自分の言葉で説明できる
  2. このレッスンの最小コード (または操作手順) を見ずに書ける
  3. 練習問題やクイズで間違えた箇所を読み直して理解した

理解度チェック (30 秒)

Q. 三項演算子 とは何か、1 文で説明してください。

この章のポイント

A. 本文の「このレッスンで分かること」または冒頭の説明文を見直し、自分の言葉で要約できれば OK。詰まったら本レッスンの最初の H2 セクションを読み返してみましょう。

関連レッスン

要件

  1. クラス名は Solution、メソッド名は absoluteValue、引数は int n 1 つ、戻り値の型は int
  2. 三項演算子 条件 ? 真の値 : 偽の値 を使って実装すること (if 文は使わない)
  3. 負の数を渡したときは符号を反転した値 (-n) を、0 以上なら n をそのまま返すこと

入出力例

test-cases.txt

absoluteValue(-5)5 absoluteValue(7)7 absoluteValue(0)0 absoluteValue(-100)100

ヒント

main.java
main.java
学習モード

メモ

三項演算子

⌘S で保存