- Home /
Efficient way to find nearest object with component
Hello,
So as the title suggests, I'm looking for a way to find the nearest object with a certain component that causes the least lag. Using OverlapSphere causes too much lag if there's too many game objects nearby, and this is due to the fact that I use tiny cubes with colliders as blood. (9 in total).
Is there perhaps a better way to fix this lag problem I'm having?
Code for Detection:
public void senseEnemiesNearby(float radius){
if (target == null) {
Collider[] hitColliders = Physics.OverlapSphere(transform.position, radius);
senseEnemies = true;
savedLoc = loc;
Cube cub = GetClosestEnemy (hitColliders, radius);
if (cub != null) {
if (cub.team != team) {
setTarget (cub);
}
}
}
}
private Cube GetClosestEnemy(Collider[] enemies, float radius)
{
Cube cub = null;
float minDist = radius;
Vector3 currentPos = transform.position;
foreach (Collider c in enemies)
{
if (c.gameObject != gameObject) {
if (c.gameObject.GetComponent<Cube> () != null && c.gameObject.GetComponent<Cube> ().team != team) {
Transform t = c.transform;
float dist = Vector3.Distance(t.position, currentPos);
if (dist < minDist)
{
cub = c.gameObject.GetComponent<Cube> ();
minDist = dist;
}
}
}
}
return cub;
}
Thanks HighlordWeaponry
Answer by Bunny83 · Dec 05, 2017 at 04:53 AM
Here are three general performance boosters to your algorithm:
First of all you may want to use layers. OverlapSphere has an additional layermask parameter.
Next you shouldn't use GetComponent more than once per object. Currently you use GetComponent up to 3 times per object. Just create a local variable inside the foreach loop and get the component once.
Finally when sorting objects based on the distance it's faster to compare sqrMagnitude. It of course doesn't tell your the actual distance but the greater than / lower than relation will stay the same.
So do something like this:
public LayerMask layers;
public void senseEnemiesNearby(float radius)
{
if (target == null)
{
Collider[] hitColliders = Physics.OverlapSphere(transform.position, radius, layers);
senseEnemies = true;
savedLoc = loc;
Cube cub = GetClosestEnemy (hitColliders, radius);
if (cub != null)
{
setTarget (cub);
}
}
}
private Cube GetClosestEnemy(Collider[] enemies, float radius)
{
Cube cub = null;
float minDist = radius;
Vector3 currentPos = transform.position;
foreach (Collider c in enemies)
{
if (c.gameObject == gameObject)
continue;
Cube cube = c.GetComponent<Cube>();
if (cube != null && cube.team != team)
{
Transform t = c.transform.position - currentPos;
float dist = t.x*t.x + t.y*t.y + t.z*t.z; // Same as "= t.sqrMagnitude;" but faster
if (dist < minDist)
{
cub = cube;
minDist = dist;
}
}
}
return cub;
}
Note i removed your second team check in your "senseEnemiesNearby" method. Since your "GetClosestEnemy" method can only return an object that has to be on a different team the null check is enough.
How many objects are there in total and how many are usually in range of the OverlapSphere? I doubt that this actually caused much slowdown. Have you used the Profiler to narrow down your bottleneck?
Thanks for your reply. I will try it out as soon as possible. As for your answer for your question, it's mainly the cube particles that are the main problem. Currently when a target dies, he divides into 9 tiny cubes that launch in a direction, then vanish after 3 seconds. However, when having mass scale battles and having a constant range detection when no longer having a target (attack-move or guard), it can be quite laggy detecting all of those objects. The lag dies down when all of the blood cubes are gone though.
It worked! Adding layers greatly reduced the lag on the program! Thanks a lot!
Your answer
![](https://koobas.hobune.stream/wayback/20220612144008im_/https://answers.unity.com/themes/thub/images/avi.jpg)
Follow this Question
Related Questions
How to do the following 0 Answers
Random lag spikes any time processor intensive tasks a scene 0 Answers
Unity Profiler - Loading.UpdatePreloading - Huge Lag Spikes 0 Answers
how to increase performance? 1 Answer
my android game lag sometimes 0 Answers