using System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; public class SlotGroup : IEnumerable.Slot> { public struct Slot { public int slotIndex; public T item; public bool IsEmpty => item == null; } Slot[] slots; public T this[int index] { get => slots[index].item; set => slots[index].item = value; } public int SlotCount => slots.Length; public bool HasEmptySlot => Array.Exists(slots, slot => slot.IsEmpty); public SlotGroup(int slotCount) { slots = new Slot[slotCount]; for(int i = 0; i < slotCount; ++i) { slots[i] = new Slot(); slots[i].slotIndex = i; } } public SlotGroup(uint slotCount) { slots = new Slot[slotCount]; for(int i = 0; i < slotCount; ++i) { slots[i] = new Slot(); slots[i].slotIndex = i; } } public void Switch(int slotIndex1, int slotIndex2) { Debug.Assert(IsValidSlotIndex(slotIndex1) && IsValidSlotIndex(slotIndex2), "Invalid slot number"); T temp = slots[slotIndex1].item; slots[slotIndex1].item = slots[slotIndex2].item; slots[slotIndex2].item = temp; } public bool TryGetItem(int slotIndex, out T item) { item = default; if(!IsValidSlotIndex(slotIndex)) { return false; } item = slots[slotIndex].item; return item != null; } public void LoopValidSlot(Func action) { foreach(var slot in slots) { if (slot.IsEmpty) continue; if (!action(slot.item)) break; } } public Slot GetSlot(int slotIndex) { Debug.Assert(IsValidSlotIndex(slotIndex), "Invalid slot number"); return slots[slotIndex]; } public bool TryGetSlot(T item, out Slot slot) { slot = default; for(int i = 0; i < slots.Length; ++i) { if (item.Equals(slots[i].item)) { slot = slots[i]; return true; } } return false; } public void GetEmptySlots(out List emptySlots) { emptySlots = new List(); foreach(var slot in slots) { if(slot.IsEmpty) { emptySlots.Add(slot); } } } public void ClearSlot(int slotIndex) { Debug.Assert(IsValidSlotIndex(slotIndex), "Invalid slot number"); slots[slotIndex].item = default; } public bool IsValidSlotIndex(int slotIndex) { return slotIndex >= 0 && slotIndex < slots.Length; } public List ConvertAll(Converter converter) { var result = new List(); foreach(var slot in slots) { if(!slot.IsEmpty) result.Add(converter(slot.item)); } return result; } public IEnumerator GetEnumerator() => ((IEnumerable)slots).GetEnumerator(); IEnumerator IEnumerable.GetEnumerator() => slots.GetEnumerator(); }