0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

生きてるコメント / 死んでるコメント ─ コメントの本質と見極め方

Posted at

はじめに

ソフトウェア開発では、言語やプラットフォームを問わずコードの可読性や意図を補うためにコメントを書く場面があります。

ただ、コメントには「価値が残り続けるもの」と「気づかないうちに負債になるもの」があり、書き方次第で結果が大きく変わります。

特にコメントについて語られる場面では、「コメントは書かない方がいい」「コードが説明するべき」といった極論も見かけますが、大切なのはそこではなく、

そのコメントがどんな経緯で価値を失うのかを理解し、それを踏まえて書き方を選べるかどうか

という点だと考えています。
そこでこの記事では、コメント全般に通じる考え方を前提にしつつ、普段私が扱っているKotlinを題材に、死んでしまうコメントと生きるコメントの違いを整理していきます。

死んでるコメントとは何か

コメントが死ぬ理由は単純ではありません。
ただ、死んでいるコメントには共通する特徴があります。

  • コードがすでに説明していることを書いている
  • なぜこの実装なのかが書かれていない
  • あいまいな注意だけが書かれている
  • 実装の変化に耐えられない
  • ドキュメントコメント(/** */)の誤用で、内容が実装より正しそうに見えてしまう

こういったコメントは、読み手の判断材料にならず、むしろ誤解を生みます。

死んでるコメントの例

例1:コードの重複説明

/**
 * null が入る可能性があります
 */
val token: String?

→ Kotlin の型システムがすでに語っているため、コメントとしての価値はありません。

例2:実装と齟齬のある説明

/**
 * ネットワークから取得します
 */
fun fetch() = localCache.load()

→ 実装変更に追随できないコメントも、読み手を混乱させるだけです。

例3:抽象的すぎる注意書き

/**
 * 危険なので注意
 */
fun doSomething() {}

→ なぜ危険なのか、何に気をつけるべきかが分からず、意味を持ちません…。

例4:自明なドキュメントコメント

/**
 * ユーザー名を返します
 */
fun getName(): String = name

→ 形式が /** */ である分、逆に誤解を強めてしまうタイプのコメントです。

生きてるコメントとは何か

一方で、適切に機能するコメントには 意図が含まれています。

  • なぜこの実装になったのか
  • どういう前提・背景があるのか
  • コードだけでは読み取れない判断理由
  • Android/Kotlinの仕様面で知っておくべき前提
  • ドメイン固有の例外ケース

こうした情報はコードだけでは表現しきれません。
だからこそ、コメントとして残す価値があります。

生きてるコメントの例

例1:実装方針の理由

/**
 * UI スレッドでも呼ばれるため、
 * 呼び出し側に thread 切り替えを強制しない方針とし、
 * 内部で IO に寄せている。
 */
suspend fun fetchUser(): User = withContext(Dispatchers.IO) {
    repository.getUser()
}

→ 手法ではなく判断理由を言語化しているコメントです。

例2:OS 仕様を踏まえた意図

/**
 * Android 14 以降、通知権限は初期状態で OFF。
 * 初回要求は ViewModel 側で一元管理する方針。
 * Fragment/Activity だとライフサイクル分岐が増えるため。
 */
fun requestNotificationPermission() { ... }

→ バージョン依存の判断理由を適切に補足できています。

例3:Composeを理解した上での設計意図

/**
 * 再コンポーズ抑制のため、
 * MutableState は公開せず State<T> のみ expose する。
 */
val uiState: State<UiState> get() = _uiState

→ Compose特有の前提を共有することで、保守性が向上します。

例4:API 仕様に由来する例外ケース

/**
 * price = 0 は「未設定」を表す API 仕様のため、
 * Kotlin 側では null を未設定として扱う。
 */
fun mapPrice(raw: Int?): Int? { ... }

→ ドメイン固有の仕様を適切に伝え、誤解を防ぐコメントです。

コメントの生死は書いた瞬間と時間経過の両面で決まる

ここが最も重要なポイントです。
コメントが死ぬ理由は、ひとつではありません。

  • 書いた瞬間に死んでいるコメント
     (構造的に意図がなく価値がない)

  • 時間経過で死ぬコメント
     (正しかったが環境変化の速度に耐えられない)

だからこそ、書く前に「これはどちらの死に方をしやすいか?」を見極めることが大切です。

そしてもうひとつ重要なのが、

生きるコメントは、このどちらの死に方にも耐えられる構造を持っている

という点です。

意図・背景・判断理由は、実装が変わっても変わりません。
これがコメントが生き続ける理由です。

コメントを書く前に確認したいチェックポイント

コメントを書こうとしたとき、まず次の点を確認すると判断がしやすくなります。

1. この内容は、コードだけで読み取れるものではありませんか?

→ 型・命名・制御フローだけで表せるなら、コメントは不要です。

2. なぜこの実装なのかがコードから判断できますか?

→ 理由・背景が読み取れなければ、コメントとして残す価値があります。

3. 仕様変更やOS差分に依存する内容ではありませんか?

→ その場合、判断理由を明記しておくと誤解を防げます。

4. ドメイン固有の前提や例外ケースはありませんか?

→ これらはコードに表しにくいため、コメントに残すのが適切です。

5. 未来の自分(または別の開発者)が読んでも意味が残るか?

→ 読む側が迷わないかでシンプルに判断できます。

おわりに

コメントは、書くべき/書かないべきの二元論では語れません。
コメントが死ぬ背景には、

  • 書いた瞬間から死んでいるコメント
  • 時間経過で死んでいくコメント

の二種類が存在し、両方を見極めて書けるかどうかが品質を左右します。
この記事がその判断の一助になれば幸いです。

0
0
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
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?