Unity Entities --- JobComponentSystem中部分参数介绍

Unity Entities|0.2.0-preview.18

Unity Entities|官方文档

JobComponentSystem支持俩种类型的lambda表达式:

1. JobComponentSystem.Entities.ForEach(lambda)依赖于Entities,返回Entities集合通过lambda进行选择筛选

2.JobComponentSystem.Job.WithCode(lambda) 依赖于IJob且执行一次

然后呢俩种定义方式都可以通过Schedule()或者Run()方式进行运行。区别就是Run()是立即执行。

这里官方还介绍了来个关键之使用 ref 和 in。ref可以用来写更改数据,in用来只读数据的。

关于in的使用MSDN官网文档

Entities.ForEach example:

class ApplyVelocitySystem : JobComponentSystem
{
    protected override JobHandle OnUpdate(JobHandle inputDependencies)
    {
        var jobHandle = Entities
            .ForEach((ref Translation translation,
                      in Velocity velocity) =>
            {
                translation.Value += velocity.Value;
            })
            .Schedule(inputDependencies);

        return jobHandle;
    }
}

Job.WithCode example:

public class RandomSumJob : JobComponentSystem
{
    private uint seed = 1;

    protected override JobHandle OnUpdate(JobHandle inputDeps)
    {
        Random randomGen = new Random(seed++);
        NativeArray<float> randomNumbers
            = new NativeArray<float>(500, Allocator.TempJob);

        JobHandle generateNumbers = Job.WithCode(() =>
        {
            for (int i = 0; i < randomNumbers.Length; i++)
            {
                randomNumbers[i] = randomGen.NextFloat();
            }
        }).Schedule(inputDeps);


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

        JobHandle sumNumbers = Job.WithCode(() =>
        {
            for (int i = 0; i < randomNumbers.Length; i++)
            {
                result[0] += randomNumbers[i];
            }
        }).Schedule(generateNumbers);

        sumNumbers.Complete();
        UnityEngine.Debug.Log("The sum of "
                              + randomNumbers.Length + " numbers is " + result[0]);

        randomNumbers.Dispose();
        result.Dispose();

        return sumNumbers;
    }
}

关于Entities.ForEach的一些查询实体的方法:

这主要用于获取到执行Entities

WithAll<T>:查找含有T类型的component

WithAny<T,U>:同时查询多个不同类型的component,也可以只查询一个,作用等同于WithAll<T>

WithNone<T> :查询不包含有此类型组件

WithChangeFilter<T>:理解的意思感觉就是在块中☞之前修改过的数据的component

WithSharedComponentFilter :顾名思义就是选择是shared component的

WithStoreEntityQueryInField :存储查询到的Entities可以进行一些查询操作

这里官方也有一个很重要的Tips:

WithNone<T> 使用不注意可能会和WithAll<T>以及WithAny<T,U>引起冲突。这里注意一下好了。

使用举例:

return Entities.WithAll<LocalToWorld>()
    .WithAny<Rotation, Translation, Scale>()
    .WithNone<LocalToParent>()
    .ForEach((ref Destination outputData,
        in Source inputData) =>
    {
        /* do some work */
    })
    .Schedule(inputDeps);

EntityQuery 使用举例:

private EntityQuery query;
protected override JobHandle OnUpdate(JobHandle inputDeps)
{
    int dataCount = query.CalculateEntityCount();
    NativeArray<float> dataSquared
        = new NativeArray<float>(dataCount, Allocator.Temp);
    JobHandle GetSquaredValues = Entities
        .WithStoreEntityQueryInField(ref query)
        .ForEach((int entityInQueryIndex, in Data data) =>
            {
                dataSquared[entityInQueryIndex] = data.Value * data.Value;
            })
        .Schedule(inputDeps);

    return Job
        .WithCode(() =>
        {
            //Use dataSquared array...
            var v = dataSquared[dataSquared.Length -1];
        })
        .WithDeallocateOnJobCompletion(dataSquared)
        .Schedule(GetSquaredValues);
}

Shared component 使用示例:

public class ColorCycleJob : JobComponentSystem
{
    protected override JobHandle OnUpdate(JobHandle inputDeps)
    {
        List<Cohort> cohorts = new List<Cohort>();
        EntityManager.GetAllUniqueSharedComponentData<Cohort>(cohorts);
        NativeList<JobHandle> dependencies
            = new NativeList<JobHandle>();

        foreach (Cohort cohort in cohorts)
        {
            DisplayColor newColor = ColorTable.GetNextColor(cohort.Value);
            JobHandle thisJobHandle
                = Entities.WithSharedComponentFilter(cohort)
                    .ForEach((ref DisplayColor color) => { color = newColor; })
                    .Schedule(inputDeps);
            dependencies.Add(thisJobHandle);
        }

        return JobHandle.CombineDependencies(dependencies);
    }
}

捕获之后参数方法:

这主要用于获取到Entities执行完lambda之后进行的一些参数设置

WithReadOnly(myvar):改变获取到的数据访问限制给成只读

WithDeallocateOnJobCompletion(myvar):完成操作之后释放本容器

WithNativeDisableParallelForRestriction(myvar):官方说法挺晦涩,感觉说人话就是可以允许多个线程访问本组数据,但是可能会额外消耗一点性能

WithNativeDisableContainerSafetyRestriction(myvar):这个官方大体的意思感觉就是关闭多线程访问保护你们尽管来,不要命的一种操作

WithNativeDisableUnsafePtrRestrictionAttribute(myvar):理解起来太头疼了(官方直译:允许您使用本机容器提供的不安全指针。不正确的指针使用可能导致应用程序中出现细微的错误、不稳定和崩溃

Job options介绍:

JobHandle Schedule(JobHandle):

    Entities.ForEach 中:可以并行执行在线程上执行lambda函数

     Job.WithCode 中:执行一个单独的实例在后台线程中

void Run():

  Entities.ForEach 中:执行一次lambda操作,不接受参数,也不返回参数

      Job.WithCode 中:执行一次

WithBurst(FloatMode, FloatPrecision, bool):设置Brust编译器信息:

  floatMode :浮点数优化模式,快速模式速度快但是也可能产生不必要的错误

       floatPrecision :设置浮点数学精度

         synchronousCompilation:立即编译该函数,而不是调度该函数以供以后编译。

WithoutBurst():禁止使用Brust编译器

WithStructuralChanges() :在主线程上执行lambda函数并禁用Burst,以便可以对函数中的实体数据进行结构更改。为了获得更好的性能,可以使用一个并发的EntityCommandBuffer

WithName(string):将指定的字符串指定为生成的作业类的名称。指定名称是可选的,但可以帮助在调试和分析时识别函数。

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

发布了71 篇原创文章 · 获赞 89 · 访问量 8万+

猜你喜欢

转载自blog.csdn.net/u012371712/article/details/104213957