RaycastCommand is somehow faster in editor?

Hey All,

I’ve created a scene with some terrain and I am casting 1000000 rays in random directions to profile RaycastCommand performance on different machines.

For some reason I am finding that the performance in editor is almost 2x that of a deployed build? Code below:

using UnityEngine;
using Unity.Collections;
using Unity.Jobs;
using System.Diagnostics;
using TMPro;
using System.Collections.Generic;
using System.Linq;

public class RaycastTester : MonoBehaviour
{
    private int N_Rays = 1000000;
    private int trials = 0;
    private NativeArray<RaycastCommand> Ray_Commands;
    private NativeArray<RaycastHit> Cast_Results;
    private TextMeshPro my_text;
    private List<long> trial_times;

    void Start ()
    {

        RaycastCommand[] mCommands = new RaycastCommand[N_Rays];
        for (int i = 0; i < N_Rays; ++i)
        {
            Vector3 this_direction = Random.onUnitSphere;
            mCommands[i] = new RaycastCommand(Vector3.zero, this_direction.normalized, 250);
        }
        Ray_Commands = new NativeArray<RaycastCommand>(mCommands, Allocator.Persistent);
        Cast_Results = new NativeArray<RaycastHit>(N_Rays, Allocator.Persistent);

        TextMeshPro[] tmpro = Object.FindObjectsOfType<TextMeshPro>();
        my_text = tmpro[0];

        trial_times = new List<long>(100);
    }

    private void OnApplicationQuit()
    {
        Ray_Commands.Dispose();
        Cast_Results.Dispose();
    }

    void Update ()
    {
        Stopwatch st = new Stopwatch();
        st.Start();

        JobHandle Cast_Job = RaycastCommand.ScheduleBatch(Ray_Commands, Cast_Results, 1);
        Cast_Job.Complete();

        st.Stop();

        trial_times.Add(st.ElapsedMilliseconds);
        ++trials;

        my_text.SetText(string.Format("{0} ms", Mathf.Round((float)trial_times.Average())));

    }
}

One thing is your test is invalid because your raycasts are randomized. Combine that with you are testing averages and over time.

Basically you are introducing variation per run, plus the averaging method is bluring it all. So while 2x seems unlikely, it’s still possible your testing methodology accounts for most of the difference.

This could also be scheduling related. Try putting JobHandle.ScheduleBatchJobs before you complete. Not sure if that’s actually done automatically for raycast jobs or not but would be interesting to see if it has an impact.

Also get rid of your averaging and just spit out the current time taken. It could also be other things running are impacting the times and the averaging doesn’t let you correlate what is happening in that frame from other frames.

Using the profiler should show something about why things are different.

I’ve taken your input and updated the vectors to be deterministic. I also am now displaying the raycasts live. Below is the modified code:

using UnityEngine;
using Unity.Collections;
using Unity.Jobs;
using System.Diagnostics;
using TMPro;
using System.Collections.Generic;
using System.Linq;

public class RaycastTester : MonoBehaviour
{
    private int N_Rays = 1000000;
    private int trials = 0;
    private NativeArray<RaycastCommand> Ray_Commands;
    private NativeArray<RaycastHit> Cast_Results;
    private TextMeshPro my_text;
    private List<long> trial_times;
    private Stopwatch st;
    private JobHandle Cast_Job;

    void Start ()
    {
        st = new Stopwatch();

        RaycastCommand[] mCommands = new RaycastCommand[N_Rays];
        for (int i = 0; i < N_Rays; ++i)
        {
            Vector3 this_direction = new Vector3(i - N_Rays, N_Rays - i, i);
            mCommands[i] = new RaycastCommand(Vector3.zero, this_direction.normalized, 250);
        }
        Ray_Commands = new NativeArray<RaycastCommand>(mCommands, Allocator.Persistent);
        Cast_Results = new NativeArray<RaycastHit>(N_Rays, Allocator.Persistent);

        TextMeshPro[] tmpro = Object.FindObjectsOfType<TextMeshPro>();
        my_text = tmpro[0];

        trial_times = new List<long>(50);
    }

    private void OnApplicationQuit()
    {
        Ray_Commands.Dispose();
        Cast_Results.Dispose();
    }

    void Update ()
    {
        st.Reset();
        st.Start();

        Cast_Job = RaycastCommand.ScheduleBatch(Ray_Commands, Cast_Results, 1);
        JobHandle.ScheduleBatchedJobs();
        Cast_Job.Complete();

        st.Stop();

        if (trials < 50)
        {
            trial_times.Add(st.ElapsedMilliseconds);
            ++trials;
        }

        // my_text.SetText(string.Format("{0} ms", Mathf.Round((float)trial_times.Average())));
        my_text.SetText(string.Format("{0} ms", st.ElapsedMilliseconds));


    }
}

Somehow I still get the same results, and strangely enough if I do something like open up slither.io while the profiler is running (to try and task the system more), I get marginally improved performance (230ms vs 270ms), and then when I close slither.io, the performance returns back to when my system is idle…

Strange. My gut reaction is differences in scheduling/completion rather then actual time in raycasting. But there isn’t really a way to time the actual raycasting. Or maybe it’s using burst in some limited fashion internally, enough to give it an edge in the editor?

Yeah, one detail I left out is that sometimes the editor will have the same performance as a deployed build, depending on the run…

I’ve looked at the profiler during both of these instances and the output to my game is the same as what the profiler reports in either case…

The scene is just a bunch of terrain features and there are no physics objects or anything. The memory profile seems to be the same for either case too…

Hm, 2018.2 has support for Burst in standalone builds. @snacktime , which version are you using?

Maybe you’re CPU is just load scaling. When benchmarking, try turning that off. On windows, go to your Advanced power options and change the minimum and maximum processor state to 100% for the duration of the test.

Hmm… I just checked and then confirmed that I am always running at 100% processor state… Good idea though!