- Home /
Why is Unity freezing with this code?
I have clones of a cube at every position in a box of 10x10x10 with a step of 0.25 (40 cubes in the x direction, 40 cubes in the y direction, and 40 cubes in the z direction). I am trying to change the transparency of the cubes based on a text file, which has 64000 lines (with the first column corresponding to x values, the second column to y values, the third column to z values, and the fourth column to transparency values). I put this script on the cube, which is then cloned, so every cube has that script attached to it.
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using UnityEngine;
using System.IO;
using System;
using System.Runtime.InteropServices;
using System.Security.Cryptography;
public class FileManager : MonoBehaviour
{
public Renderer rend;
public Color color;
string filePath, fileName;
void Update()
{
if (Input.GetKeyDown("space"))
{
StartCoroutine(Delay());
}
}
void LateUpdate()
{
Color color = this.GetComponent<MeshRenderer>().material.color;
rend = GetComponent<Renderer>();
if (color.a == 0)
{
rend.enabled = false;
}
}
public IEnumerator Delay()
{
for (int i = 3; i <= 3; i++)
{
rend.enabled = false;
fileName = "Wave_Time_" + i + ".txt";
filePath = Application.dataPath + "/" + fileName;
ReadFromTheFile();
yield return null;
}
}
public class Point
{
public float x { get; set; }
public float y { get; set; }
public float z { get; set; }
public float p { get; set; }
}
public void ReadFromTheFile()
{
List<Point> Points = new List<Point>();
List<string> lines = File.ReadAllLines(filePath).ToList();
foreach (var line in lines)
{
string[] entries = line.Split(',');
Point newPoint = new Point();
newPoint.x = float.Parse(entries[0]);
newPoint.y = float.Parse(entries[1]);
newPoint.z = float.Parse(entries[2]);
newPoint.p = float.Parse(entries[3]);
Points.Add(newPoint);
}
Color color = this.GetComponent<MeshRenderer>().material.color;
rend = GetComponent<Renderer>();
float index = (4 * transform.position.x) * 1600 + (4 * transform.position.y) * 40 + (4 * transform.position.z);
color.a = Points[(int) index].p;
this.GetComponent<MeshRenderer>().material.color = color;
}
}
Answer by Bunny83 · Jul 30, 2020 at 11:06 PM
Ok, just to summarize:
You created 64000 cube gameobjects in your scene and attached this script to every one of those cubes. Each of those scripts (when space is pressed) will read a file with 64k lines of text, splits each line, parses each string fragment, creates a list of the parsed data and then looks up a single value in that list based on the index....
And now you're wondering why your application hangs? Are you serious? ^^ You essentially parse over 4 BILLION lines of text. You create tons of garbage on the way, which alone would probably take minutes if not hours.
There are many things wrong with your approach. First of all creating 64k gameobject and giving each object a unique material is already the first issue. None of your objects could batch that way. However depending on the effect you're after you might not have many alternatives since batching transparent objects is quite tricky.
Next thing is none of your cubes should have a script attached unless you really need one for other purposes. For what you have shown there's absolutely no reason to have a script on the cubes. You should have a single script instance on a seperate object (maybe a parent object of the cubes) and only read and parse your file once.
Next strange thing is you said that you have the x, y and z coordinates in the file which you completely ignore. You just calculate the index based on the flattened 3d array. So since you don't use any coordinates you would only need a single value per line.
You're doing a lot of unnecessary things which just create extra garbage. Like the ToList after "ReadAllLines". All you do is iterating through that list of lines. So just use the returned array. You duplicate the whole data for no reason. I don't see any reason why "Point" is a class and not a struct. Just for storing 4 float values you could simply use Unity's Vector4 struct.