🧊 【Unity】10万オブジェクトを回転させたらどこがボトルネックになるのか(後編:ISystemで一桁msへ)

📌 この記事は Zenn に投稿した内容のアーカイブです。 はじめに 前回は、Job System + Burst を使って 10万オブジェクトの回転処理(46ms → 3.5ms) まで最適化しました。 ただしその時点でも、フレーム全体としてはまだ重く、 ボトルネックはレンダリング側に残っていました。 なぜJob Systemだけでは不十分だったのか 前回の時点で回転処理自体はかなり軽くなっていましたが、 それでもフレーム全体としては大きな負荷が残っていました。 原因は、描画周りの処理です。 たとえロジック(Job)が高速でも、メインスレッド側では依然として 10万個の MeshRenderer を個別に処理する必要があります。 具体的には以下のような処理です: Culling(可視判定) Bounding Volume(バウンディング更新) RenderQueue(描画順の整理) これらがすべて「オブジェクト単位」で実行されるため、 結果として大きなCPU負荷になっていました。 この問題に対するアプローチが、Entities Graphicsです。 目標: → GameObjectベースのオブジェクトをEntityに変換する 仕組み: → 変換後は、これらの処理を Entities Graphics が内部的に管理し、 BatchRendererGroup を利用して描画処理をまとめて実行します。 その結果: 数万〜数十万単位のオブジェクトでも、 ごく少数のバッチとして扱えるようになります。 ■ 結果 今回は DOTS(Entities + Entities Graphics)に移行した結果: フレーム時間:約120ms → 約9ms 110FPS前後で安定 ほぼ別物レベルまで改善しています。 ■ 比較 指標 改造前(GameObject) 改造後(Pure DOTS) 改善 Batches ~120,000 74 約1486倍削減 SetPass Calls 56 26 約2.1倍改善 Tris / Verts 不安定 安定 描画の一貫性向上 Frame Time 120ms(8FPS) 9ms(110FPS) 約13倍高速化 ■ Profilerを見ると何が起きているか Profilerを確認すると: ...

2026年4月1日 · 3 分 · 612 文字 · Wuyukwi

🧊 【Unity】10万オブジェクトを回転させたらどこがボトルネックになるのか(前編:LateUpdateとJob System)

📌 この記事は Zenn に投稿した内容のアーカイブです。 最近、DOTS(Data-Oriented Tech Stack)が実際どのくらい効果があるのか気になっていたので、 簡単な検証を兼ねて触ってみることにしました。 せっかくなので「大量のオブジェクトを動かした場合にどこがボトルネックになるのか?」も含めて、 段階的に確認していこうと思います。 この記事ではまず、LateUpdateでの回転処理のボトルネックと、 Job Systemによる最適化の効果にフォーカスします。 レンダリング周り(CullingやDrawCall)については、次回以降で触れる予定です。 ■ 検証環境 CPU:i7-12700K GPU:RTX 3070 Unity:URPの新規プロジェクト オブジェクト数:10万(Cube) ■ テスト内容 シンプルに「10万個のCubeを生成して回転させるだけ」です。 BoxColliderは削除 ランダム位置に配置 各オブジェクトにランダムな回転軸 void Start() { var root = new GameObject(“CubeRoot”).transform; for (int i = 0; i < spawnCount; i++) { var go = Instantiate(prefab, Random.insideUnitSphere * 50f, Quaternion.identity, root); transforms.Add(go.transform); } } void LateUpdate() { float dt = Time.deltaTime; for (int i = 0; i < transforms.Count; i++) { transforms[i].Rotate(rotationAxes[i], 100f * dt); } } ...

2026年3月31日 · 2 分 · 362 文字 · Wuyukwi