ゲーム開発が形になってくると避けて通れないのが「最適化」です。今回は、私が本格的に最適化に取り組み始めたなかで、一般的かつ即効性のある具体的な事例を紹介していきます。

Tickで時間をカウントアップし、閾値を超えたらDestroyActor。ロジックとしては非常にシンプルで、つい書いてしまいがちな処理ですよね。
1. 寿命のあるActorは「Initial Life Span」で管理する
実は、先ほどの「シンプルに見えるTick処理」が大きな落とし穴でした。マシンガンから排出される薬莢(エフェクト)1つ1つにこのTickを実装した結果、30秒間で10万回も実行され、CPU時間を0.1秒ほど食いつぶしていました。
こうした単純な「寿命(ライフスパン)」による消去は、自分でカウンタを作る必要はありません。Actorの設定にある「Initial Life Span」という項目に秒数を指定するだけで解決します。

これだけで、BeginPlayから指定時間経過後に自動でDestroyActorされます。Tickをまるごと廃止できるため、10万回もの不要な呼び出しを削減できました。
1回1回の処理は軽量でも、Tickは実行待ちの行列を作るため、呼び出し回数が増えるだけで無視できないコストになります。特にBlueprintのTickはC++に比べてかなり重いと言われているので注意が必要です( ;∀;)
ボトルネックの特定には「Unreal Insights」でログを取り、解析にAIを活用するのも今の時代らしい方法です。


Insightsの画像をそのままAIに見せてもいいですが、絞り込んだ統計表のテキストデータを渡すと、Gemini/ChatGPT等の無料プランでもかなり精度高くアドバイスをくれますよ。
2. 周期的なタスクは「Timer」へ移行する
Tickで行っている処理の多くは、「Timer(Set Timer by Event/Function Name)」で代用可能です。毎フレーム実行しなければならない超高頻度な処理以外は、適切な周期のタイマーに切り替えましょう。

Timer化するメリットは、負荷軽減だけではありません。
- 処理ごとに個別の周期を設定できる(クールダウン管理変数が不要になる)
- 必要なときだけ開始・停止・再開をコントロールしやすい

敵の索敵なんかは、超高速で動く相手を追うのでなければ、0.1秒〜0.2秒間隔(秒間5〜10回)くらいでもゲーム的には十分違和感ないですよね。
3. どうしてもTickが必要なら「Tick Interval」で頻度を落とす
「Tick=毎フレーム実行」と思われがちですが、実はその実行頻度は制御可能です。Actorプロパティの「Tick Interval」を活用しましょう。

例えば60FPSで動作している場合、デフォルト(0.0)では約0.016秒間隔で処理が走ります。ここを「0.1秒」に設定すれば、約6フレームに1回の実行まで頻度を落とせます。これだけでもパフォーマンスにかなりの余裕が生まれるはずです。
中級者向けおまけ
Significance Manager を活用する(高度・C++前提)
UE5公式の最適化プラグインで、プレイヤーからの距離や画面内での重要度に応じて、動的にTick頻度を変化させることができます。
- 仕組み:
- プレイヤーの近くにいるNPCは毎フレーム更新。
- 遠くにいるNPCは
0.1秒や0.5秒おきに更新。 - 画面外のNPCは更新停止。
- メリット:
- 常に一定間隔で間引くよりも、ゲーム体験を損なわずに劇的な最適化が可能です。

EQSみたいに、重要度を判定してTick頻度を変える仕組みのようです。わざわざその計算処理をする価値があるほどTickが重い証拠でもあるともいえますね。
わからないで使おうとすると、大事なところで動いてくれないバグの原因にもなりえるので、初心者はまず今回の記事のような基礎を抑えましょう

コメント