Значения нулевого элемента массива объектов отображаются некорректно

Есть область/поле, в которую генерируются ячейки. Ячейки при создании получают данные из ScriptableObject в рандомном порядке, но почему-то получается так, что 0ой элемент данные не получает, или получает, но последнее значение предыдущей генерации. Например: (1ый запуск: null, 1, 2 => 2ой: 2, 2, 1 => 3ий: 1, 2, 1). Я сделал костыль, создавая на 1 элемент больше, и удаляя 0ой элемент, что в принципе решило проблему, но получаю ошибку:

ArgumentOutOfRangeException: Index was out of range. Must be non-negative and less than the size of the collection. Parameter name: index

Получается, что я вышел за диапазон, но как это поправить без костылей, не понимаю. Может кто-нибудь помочь разобраться?

public class Field : MonoBehaviour
{

    [Tooltip("Список настроек для иконок")]
    [SerializeField] private List<CardData> cardDataList;

    [Tooltip("Кол-во объектов в пуле")]
    [SerializeField] private int FieldSize;

    [Tooltip("Базовый префаб иконок")]
    [SerializeField] private GameObject cellPref;

    [SerializeField] private float CellSize;
    [SerializeField] private float Spacing;

    [SerializeField] private RectTransform rt;

    private Cell cellCell;
    private GameObject[] field;
    private int rand;
    private List<int> randomList = new List<int>();

    void Start()
    {
        randomList = new List<int>(new int[cardDataList.Count]);
        GenerateField();
    }
    
    private void CreateField()
    {
        randomWithoutDuplicate();

        field = new GameObject[FieldSize]; //инициализируем массив
        float fieldWidth = FieldSize * (CellSize + Spacing) + Spacing; // считаем ширину поля
        rt.sizeDelta = new Vector2(fieldWidth, CellSize + Spacing); // устанавливаем размер на canvas
        float startX = -(fieldWidth / 2) + (CellSize / 2) + Spacing; // нач.позиции для первой клетки
        float startY = (fieldWidth / 2) - (CellSize / 2) - Spacing;

        var sprite = cellPref.GetComponent<Cell>();

        //заполняем поле и создаём объекты по префабу
        for (int x = 0; x < FieldSize+1; x++)
        {
            var cell = Instantiate(cellPref, transform, false); //startY - (y * (CellSize + Spacing))

            sprite.Init(cardDataList[randomList[x]-1]); // присваиваем элементу данные из базы cardDataList
            Debug.Log(cardDataList[randomList[x]-1] + " <<=====");

            var position = new Vector2(startX + (x * (CellSize + Spacing)), 0);
            cell.transform.localPosition = position;

            field[x] = cell; // созданный объект заносим в массив
            if(field[0])
                Destroy(field[0]); // костыль удаляющий неправильно заполняющийся элемент
        }
        

        
    }

    private void randomWithoutDuplicate()
    {
        for (int i = 0; i < cardDataList.Count; i++)
        {
            rand = UnityEngine.Random.Range(1, cardDataList.Count + 1);
            while (randomList.Contains(rand))
            {
                rand = UnityEngine.Random.Range(1, cardDataList.Count + 1);
            }
            randomList[i] = rand;
            Debug.Log(randomList[i]);
        }
    }

    private void GenerateField()
    {
        if (field == null)
    }
    
}

введите сюда описание изображения


Ответы (2 шт):

Автор решения: Сherubim

Используя в цикле Length или Count, вроде как всегда нужно прописывать -1, то есть:

for(int i =0; i <= (carDataList.Count - 1); i++)
→ Ссылка
Автор решения: at0m

Оказалось, что sprite.Init(cardDataList[randomList[x]-1]), который присваивал данные элементам надо было использовать ДО создания первого элемента (который и не получал данные). Сама рандомная генерация также претерпела изменения.

private void CreateField()
{
    var asd = randomWithoutDuplicate(); // генерируем очередь без повторов
    
    field = new GameObject[FieldSize]; //инициализируем массив
    float fieldWidth = FieldSize * (CellSize + Spacing) + Spacing; // считаем ширину поля
    rt.sizeDelta = new Vector2(fieldWidth, CellSize + Spacing); // устанавливаем размер на canvas

    float startX = -(fieldWidth / 2) + (CellSize / 2) + Spacing; // нач.позиции для первой клетки
    float startY = (fieldWidth / 2) - (CellSize / 2) - Spacing;

    var sprite = cellPref.GetComponent<Cell>();
    //заполняем поле и создаём объекты по префабу
    for (int x = 0; x < field.Length; x++)
    {
        sprite.Init(cardDataList[asd[x]]); //передаём данные до создания 1ого элемента, иначе он не будет получать данные
        var cell = Instantiate(cellPref, transform, false);
        var position = new Vector2(startX + (x * (CellSize + Spacing)), 0);
        cell.transform.localPosition = position;

        field[x] = cell; // созданный объект заносим в массив
    }
}

private List<int> randomWithoutDuplicate()
{
    var rnd = new System.Random();
    var randomNumbers = Enumerable.Range(0, cardDataList.Count).OrderBy(x => rnd.Next()).Take(cardDataList.Count).ToList();

    return randomNumbers;
}
→ Ссылка