Search Unity

Array order changed on compile

Discussion in 'Getting Started' started by ericbintner, Sep 10, 2019.

  1. ericbintner

    ericbintner

    Joined:
    Jul 22, 2019
    Posts:
    23
    I'm experiencing an issue with looping through an array. I expect the order to be the same in the Game window build and the final build, but it appears to be changing the hierarchy order (and therefor the index order) in the compile. Just a guess.

    Basically I have 4 doors that I'm adding to an array, in the Game environment in Unity they seem to correlate with the order in the hierarchy. In the following example one door opens, the first one: Door[0]. When compiled and tested in iPhone this code makes the third door open. Not sure why the first door in the hierarchy isn't the first door after compile.

    Code (CSharp):
    1. public GameObject[] Door;
    2.  
    3. void Start()
    4. {
    5.     Door = GameObject.FindGameObjectsWithTag("Door");
    6.  
    7.     for(int i = 0; i < Door.Length; ++i)
    8.     {
    9.         Door[0].transform.DOMoveY( -1f, 1f);
    10.     }
    11. }
    - - - - - - -
    Also I cannot tag this thread with C#, array, or loop so I didn't tag it at all.
     
    Last edited: Sep 10, 2019
  2. Vryken

    Vryken

    Joined:
    Jan 23, 2018
    Posts:
    771
    If you need a specific order of items in a collection, don't rely on any of the "Find" methods to populate the collection - set them manually from the inspector.

    If setting them manually isn't an option, then you can attach a script onto each door object to assign it an ID:
    Code (CSharp):
    1. public class Door : MonoBehaviour {
    2.    public int doorID;
    3. }
    Then after finding all these objects, sort them by their IDs before storing them in your array:
    Code (CSharp):
    1. public Door[] doors;
    2.  
    3. void Start() {
    4.    Door[] foundDoors = FindObjectsOfType<Door>();
    5.  
    6.    //using System.Linq
    7.    doors = foundDoors.OrderBy(door => door.doorID).ToArray();
    8. }
    The downside here being that you need to manually ensure that each Door's ID is unique in the scene.
     
    Last edited: Sep 10, 2019
    ericbintner likes this.
  3. ericbintner

    ericbintner

    Joined:
    Jul 22, 2019
    Posts:
    23
    Huh, It's weird because I leaned to dynamically do this with javascript 10 years ago so it feels like I've lost 10 years of experience by manually naming each item. Is this because Unity just doesn't bother keeping the order the same or that I'm misunderstanding something fundamental about C#?
     
  4. JoeStrout

    JoeStrout

    Joined:
    Jan 14, 2011
    Posts:
    8,130
    You're just relying on undocumented behavior, which is never a good idea. FindObjectsOfType doesn't make any claim about what order the objects will be found in. Hopefully under the hood it's doing something that makes it find things fast (such as using a hash table), even if that doesn't preserve order (such as a hash table).

    To rely on a particular order from a function that makes no claims about order is simply incorrect programming, no matter what language you're using.
     
    Bill_Martini likes this.
  5. JeffDUnity3D

    JeffDUnity3D

    Unity Technologies

    Joined:
    May 2, 2017
    Posts:
    5,133
    Collections have no explicit ordering.
     
    Joe-Censored likes this.