You are editing the list you are walking.

The problem
The list shrinks under the loop.
foreach ( var child in GameObject.Children ){ child.Destroy();}
Children is the live list. Removing item 0 slides every other item down, so the loop skips one each time.
What you actually get
It deletes every other one.
Six children in, three left behind.
- Start
- six children
- After the loop
- three still there
- Run it again
- one or two left
It looks intermittent, which is why this one survives testing.
The fix
Copy the list, then walk the copy.
foreach ( var child in GameObject.Children.ToList() ){ child.Destroy();}
ToList takes a snapshot. The loop walks that, and the real list is free to change underneath.
The rule
Never change a list you are walking.
- Deleting children
- ToList first
- Removing from a List
- loop backwards
- Filtering
- build a new list
A plain List throws. An engine list just skips.