可読性の高い変数名の全体像
変数名は「コードの意味を最短で伝えるラベル」です。可読性の高い名前は、型や実装に頼らず「何を表し、どの単位・範囲・状態か」を一目で分かるようにします。Java では小文字のキャメルケース(lowerCamelCase)が基本。略語や曖昧語を避け、意図を明文化することで、理解速度とバグ耐性が上がります。
命名の基本ルールとスタイル
キャメルケースと英語の自然さ
- スタイル:
lowerCamelCase(例:userName,maxRetryCount)。クラスはUpperCamelCase(例:UserService)。 - 英語の自然さ: 検索しやすい一般的な単語を使う(
get,update,total,list)。造語や社内用語は避け、必要なら補足コメントを添える。 - 略語の扱い: 認知された略語のみ(
id,url,api)。それ以外はフルスペル(count、number、message)。
役割を動詞+名詞で示す
- 状態:
isActive,hasError,shouldRetry(真偽は「質問文」)。 - コレクション:
users,userList,userById(複数形や構造を反映)。 - 動作結果:
result,sum,totalPrice(何の合計か明記)。
意味を具体化するテクニック(重要ポイントの深掘り)
範囲・単位・型のニュアンスを名前に埋め込む
- 単位:
timeoutMs,fileSizeBytes,progressPct(ミリ秒・バイト・パーセント)。 - 範囲:
maxRetries,minAge,upperBoundExclusive(排他/包括を明示)。 - 形式:
dateIso,priceWithTax,normalizedText(加工済みかを示す)。
こうすることで、コメントなしでも誤用が減ります。
文脈を持つ接頭辞・接尾辞
- 接頭辞:
dbUser,apiRequest,uiModel(層やソースの起点)。 - 接尾辞:
Map,List,Set,Queue,Optional(構造や有無を表す)。例:userByIdMap,pendingTasksQueue,maybeUser。
過度に冗長にならないように「必要十分」を意識します。
真偽値は否定形を避ける
- 悪い例:
notFound(二重否定が起きやすい) - 良い例:
exists,isFound,hasItem - 分岐の読みやすさ:
if (hasPermission) { ... }は意図が直感的。
変数の寿命とスコープに合わせた命名
スコープが短いなら簡潔、長いなら説明的に
- 短寿命(数行):
i,j,tmpは許容。ただし用途が明確なループだけ。 - 長寿命(メソッド・クラス跨ぎ): 省略しないで説明的に(
index、buffer,currentUserId)。
ループ・イテレーションのパターン
- コレクション:
for (User user : users) { ... }(要素名は単数形) - インデックス:
for (int index = 0; index < items.size(); index++) { ... }(iが曖昧ならindex)
悪い命名を良い命名へ(重要ポイントの深掘り)
曖昧語・汎用語の置き換え
- Bad:
data,info,value,flag - Good:
userProfileJson,orderTotal,retryEnabled,errorCode
何のデータか・形式は何か・用途は何かを具体化します。
同音異義・紛らわしい略語の回避
- Bad:
cnt,num,val(読み手が文脈を推測する必要あり) - Good:
itemCount,customerNumber,currentValue(推測不要に)
マジックナンバーを名前に昇格
// 悪い
if (score >= 70) { /* ... */ }
// 良い
final int PASS_THRESHOLD = 70;
if (score >= PASS_THRESHOLD) { /* ... */ }
Java名前で「意味」を伝え、後から変更も容易になります。
例題で身につける
例 1: リファクタ前後の比較
// Before
String s1 = getData();
String s2 = normalize(s1);
if (check(s2)) process(s2);
// After
String rawUserCsv = fetchUserCsv();
String normalizedCsv = normalizeCsv(rawUserCsv);
boolean hasValidHeader = hasValidHeader(normalizedCsv);
if (hasValidHeader) processCsv(normalizedCsv);
Java意図が可視化され、追跡しやすくなります。
例 2: 単位・範囲・構造を名前に含める
long timeoutMs = 2_000;
int maxRetries = 3;
java.util.Map<String, User> userByIdMap = new java.util.HashMap<>();
java.util.List<User> activeUsers = new java.util.ArrayList<>();
boolean shouldRetry = (errorCount < maxRetries);
Java誤用の余地が減り、境界条件が読み取りやすくなります。
例 3: 真偽値を質問文で表現
boolean isAdult = age >= 18;
boolean hasText = s != null && !s.isBlank();
boolean canSubmit = isAdult && hasText;
Java条件式の意味が脳内翻訳なしで理解できます。
チームで揃えるための運用ヒント
プロジェクト標準の言語・辞書を用意
- 語彙の共有: ドメイン語彙リスト(例:顧客=
customer、取引=transaction、受注=order)。 - スタイルガイド: 小文字キャメル、真偽の接頭辞(
is/has/should/can)、コレクションの接尾辞(List/Map/Set)などを文書化。
IDE の支援を活用
- 自動補完とリネーム: 一括リネームで安全に改善、
Search Everywhereで曖昧語を見つけて置換。 - 検査: Lint/静的解析のルール(長すぎる名前、スコープ外参照など)を導入。
仕上げのアドバイス(重要部分のまとめ)
- 意味の具体化: 単位・範囲・構造・状態を名前に含める。
- 真偽の質問文:
is/has/should/can接頭辞で条件を読みやすく。 - スコープと寿命: 短命は簡潔、長命は説明的に。
- 汎用語禁止:
data/value/flagは具体語へ置換。 - 一貫性: キャメルケース・複数形・接尾辞(
List/Map)をプロジェクト標準で揃える。
