Need help with my view distance script, and if i can either A. optimize it or B. split a table into multiple pieces.

So, what im trying to accomplish here is to make a view distance script for the camera, and im trying to optimize it, as i have about 175k objects in the scene(an open-world game), and its laggy each frame it detects the view distance and i want to fix it somehow. Please help!

here is my code:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class ViewDistance : MonoBehaviour
{
    // Start is called before the first frame update
    public GameObject Parent = null;
    public WorldValues values;
    GameObject RootPart = null;
    Vector3 OldPlayerPos;
    public float MaxDistance;
    public float MaxItems;
    public float TickSpeed = 1;
    bool cantickagain = true;

    public bool cam;
    void Start()
    {
        RootPart = values.RootPart;
    }

    // Update is called once per frame
    void Update()
    {
        if (OldPlayerPos != values.MainCamera.transform.position)
        {
            if (cantickagain)
            {
                foreach (Transform object1 in Parent.transform)
                {
                    Vector2 camdis = new Vector2(values.MainCamera.transform.position.x, values.MainCamera.transform.position.z);
                    Vector2 objdis = new Vector2(object1.transform.position.x, object1.transform.position.z);
                    if (Vector2.Distance(camdis, objdis) > MaxDistance)
                    {
                        object1.gameObject.SetActive(false);
                    }
                    else
                    {
                        object1.gameObject.SetActive(true);
                    }
                }
                OldPlayerPos = values.MainCamera.transform.position;
            }
        }


        if (cantickagain)
        {
            IEnumerator tick()
            {
                cantickagain = false;
                yield return new WaitForSeconds(TickSpeed);
                cantickagain = true;
            }
            StartCoroutine(tick());
        }
    }
}

There are multiple things you can do.

Though the best you can do to begin with is to actually check the profiler what actually takes up all the performance. You should never optimize blindly.

Howevery an easy improvement would be to not get the Distance but the squared distance instead.

 if (camdis - objdis).sqrMagnitude > MaxDistance

where in your start function you add the line:

  MaxDistance *= MaxDistance

This will greatly improve performance but you might have to turn MaxDistance into a long

Why is this faster you ask? → Because distance is the squareroot of the squares of the vector elements. Calculating the squareroot is really really slow.

Apart from this you should consider to group your objects on a grid. Then you only have to check your players position if it moves into a new grid element. So for example your grid has a size of 50x50 units.
You have a 2D list of all grid elements which in turn each contain a reference to all objects which are positioned within. (This can already be setup in your scene so takes up no performance at runtime)

Assuming your player starts at grid (0,0). At startup you can disable all objects in grid elements which are lets say between -4 and 4 in x and y direction.

Then when your player for example leaves grid element (0,0) for grid element (0,1) you disable all objects in grid elements (-4 to 4, -4) and enable all objects in grid elements (-4 to 4, 5).

This can then be further optimized by creating a routine which only enables and disables like 5 objects per frame so that your game is not overloaded on the instance you move from one grid to another.

Games like minecraft for example use similar system. There the grid elements are called “chunks”.

Hope this helps, let me know if something was unclear.