Version: 2021.3
C# Job System の安全システム


データをコピーする 安全システム による処理の欠点は、各コピー内のジョブの結果も単独化してしまうことです。この制限を解決するには、NativeContainer と呼ばれる共有メモリに結果を保存する必要があります。

A NativeContainer is a managed value type that provides a safe C# wrapper for native memory. It contains a pointer to an unmanaged allocation. When used with the Unity C# Job System, a NativeContainer allows a job to access data shared with the main thread rather than working with a copy.

Types of NativeContainer

Unity には、NativeArray と呼ばれる NativeContainer が搭載されています。NativeArrayNativeSlice で操作して、NativeArray の特定の位置から特定の長さのサブセットを取得することもできます。

Note: The Entity Component System (ECS) package extends the Unity.Collections namespace to include other types of NativeContainer:

  • NativeList - サイズ変更可能な NativeArray
  • NativeHashMap - キーと値のペア
  • NativeMultiHashMap - 各キーに複数の値
  • NativeQueue - 先入れ先出し (FIFO) キュー

NativeContainer と安全システム

セーフティシステムはすべての NativeContainer タイプに組み込まれています。 NativeContainer へのすべての読み取りと書き込みを追跡します。

Note: All safety checks on NativeContainer types (such as out of bounds checks, deallocation checks, and race condition checks) are only available in the Unity Editor and Play mode.

Part of this safety system is the DisposeSentinel and AtomicSafetyHandle. The DisposeSentinel detects memory leaks and gives you an error if you haven’t freed your memory correctly. Triggering the memory leak error happens long after the leak occurred.

AtomicSafetyHandle を使用すると、コードの NativeContainer の所有権を移動します。例えば、2 つのスケジュールされたジョブが同じ NativeArray に書き込みを行なうと、安全システムは例外を発生させ、問題の原因と解決方法を説明する明確なエラーメッセージを示します。安全システムは、違反のジョブがスケジュールされたときにこの例外をスローします。

この場合、依存関係を持つジョブをスケジュールに組み込めます。最初のジョブは NativeContainer に書き込むことができ、実行が終了すると、次のジョブは同じ NativeContainer から安全に読み取り、または書き込みすることができます。読み取りと書き込みの制限は、メインスレッドからデータにアクセスするときにも適用されます。安全システムでは、複数のジョブが並列で同じデータから読み取ることができます。

By default, when a job has access to a NativeContainer, it has both read and write access. This configuration can slow performance. The C# Job System doesn’t allow you to schedule a job that has write access to a NativeContainer at the same time as another job that’s writing to it.

If a job doesn’t need to write to a NativeContainer, mark the NativeContainer with the [ReadOnly] attribute, like so:

public NativeArray<int> input;

上の例では、読み取り専用アクセス権を持つジョブと、NativeContainer への読み取り専用アクセス権を持つその他のジョブを同時に実行することができます。

注意 ジョブ内からの静的データへのアクセスに対する保護はありません。静的データにアクセスすると、すべての安全システムを回避し、Unity をクラッシュさせる可能性があります。詳細は、C# Job System のヒントとトラブルシューティング を参照してください。

NativeContainer アロケーター

When creating a NativeContainer, you must specify the memory allocation type that you need. The allocation type depends on the length of time the job runs. This way you can tailor the allocation to get the best performance possible in each situation.

There are three Allocator types for NativeContainer memory allocation and release. You must specify the appropriate one when instantiating a NativeContainer.

  • Allocator.Temp has the fastest allocation. Use it for allocations with a lifespan of one frame or fewer. However, you can’t use Temp to pass NativeContainer allocations to jobs.
  • Allocator.TempJob is a slower allocation than Temp but is faster than Persistent. Use it for thread-safe allocations within a lifespan of four frames. Important: You must Dispose of this type of allocation within four frames, or the console prints a warning, generated from the native code. Most small jobs use this NativeContainer allocation type.
  • Allocator.Persistent is the slowest allocation but can last as long as you need it to, and if necessary, throughout the application’s lifetime. It is a wrapper for a direct call to malloc. Longer jobs can use this NativeContainer allocation type. Don’t use Persistent where performance is essential.

NativeArray<float> result = new NativeArray<float>(1, Allocator.TempJob);

Note: The number 1 in the example above indicates the size of the NativeArray. In this case, it has only one array element because it only stores one piece of data in result.

C# Job System の安全システム
Copyright © 2020 Unity Technologies
优美缔软件(上海)有限公司 版权所有
"Unity"、Unity 徽标及其他 Unity 商标是 Unity Technologies 或其附属机构在美国及其他地区的商标或注册商标。其他名称或品牌是其各自所有者的商标。