本ページにはプロモーションが含まれます
Unity

【Unity】Pure C#を使う理由

この記事は約5分で読めます。

はじめに

開発を長く続けていると、次第にスクリプトが肥大化してきます。
MonoBehaviourにすべてのロジックを詰め込んでしまい、継承したコントローラをキャラごとに変化をつけ増産して……
後から改修しようとすると「どこを直せばいいのかわからない」という状態に陥ることは多いですよね。

そこで今回は、Unityでもっとスマートにコードを管理するための「Pure C#」の考え方とフォルダ構成を検討してみた。

Pure C#とは?

Pure C#(ピュアC#)とは、
「UnityEngineやMonoBehaviourなど、Unity固有のAPIに依存しない純粋なC#コード」を指します。

簡単に言えば、
どのC#環境でも動くように書かれたC#コード のことです。

public class DamageCalculator
{
    public static int Calculate(int attack, int defense)
    {
        return Math.Max(1, attack - defense);
    }
}

これはUnityでも、.NETのコンソールアプリでもそのまま動きます。
外部環境に依存しない「純粋なロジック」だからです。

Unity C#との違い

一方、通常のUnityスクリプトは MonoBehaviour を継承しており、
transform や GameObject など、Unityエンジンの機能に密接に結びついています。

using UnityEngine;

public class Enemy : MonoBehaviour
{
    void Start()
    {
        transform.Translate(Vector3.forward);
    }
}

このようなコードは、Unity以外では動かせません。
Pure C#ではなく「Unity依存C#」です。

なぜPure C#を使うのか?

Pure C#をプロジェクトに導入することで、
Unity開発の「長期的な伸びしろ」が一気に広がります。

1. テストがしやすい

Unityを起動せずにNUnitやxUnitで単体テストが可能です。
ロジックだけを外部ツールで確認できるのは大きなメリットです。

2. 再利用性が高い

同じコードをサーバー側、ツール側でも使い回せます。
例えば「ダメージ計算」や「ステータス管理」はどの環境でも共通です。

3. パフォーマンスが安定

TransformなどのUnityAPI呼び出しが無い分、余分なオーバーヘッドが減ります。

4. クリーンアーキテクチャに近づける

ロジック層(Pure C#)と表示層(Unity)を分けることで、
保守性が圧倒的に上がります。

Assets/
├── Scripts/
│   ├── Core/                      ← Pure C#層(Unity依存なし)
│   │   ├── Domain/                ← ゲームロジック
│   │   ├── Services/              ← 計算やデータ処理
│   │   ├── Models/                ← データ構造やクラス
│   │   ├── Interfaces/            ← 抽象インターフェース
│   │   └── Extensions/            ← 拡張メソッド
│   │
│   ├── Game/                      ← Unity層(MonoBehaviourあり)
│   │   ├── Controllers/
│   │   ├── Components/
│   │   ├── UI/
│   │   ├── Managers/
│   │   └── Playmaker/
│   │
│   ├── Editor/                    ← UnityEditor専用
│   └── ThirdParty/                ← 外部アセット
│
………

このように構成すると、ロジック層(Core) と Unity層(Game) を明確に分離でき、
将来的にどれだけ規模が大きくなっても整理された状態を保てます。

実際の使い方例

// Core/Domain/DamageCalculator.cs
namespace Game.Core.Domain
{
    public static class DamageCalculator
    {
        public static int Calculate(int atk, int def)
        {
            return Math.Max(1, atk - def);
        }
    }
}

 

// Game/Components/Enemy.cs
using UnityEngine;
using Game.Core.Domain;

public class Enemy : MonoBehaviour
{
    public int attack = 10;
    public int defense = 5;

    void Start()
    {
        int damage = DamageCalculator.Calculate(attack, defense);
        Debug.Log($"Damage: {damage}");
    }
}

これで「ロジック層」と「ゲーム層」が完全に独立します。

おわりに

項目内容
Pure C#とはUnityに依存しない純粋なC#コード
メリットテスト・再利用・保守性・パフォーマンス向上
おすすめ構成Core(Pure C#)+Game(Unity API)で分離
理想の設計クリーンアーキテクチャ/ドメイン駆動設計に近い

Coreフォルダでは 絶対に using UnityEngine; を書かない。
ロジックは staticクラス または 非MonoBehaviourクラス にする。
Game層では Pure C#の結果を受け取って表示や演出を担当。