using System; using System.Collections; using System.Collections.Generic; namespace PKHeX.Core { public class PeekEnumerator : IEnumerator { private readonly IEnumerator Enumerator; private T peek; private bool didPeek; #region IEnumerator Implementation public bool MoveNext() { if (!didPeek) return Enumerator.MoveNext(); didPeek = false; return true; } public void Reset() { Enumerator.Reset(); didPeek = false; } object IEnumerator.Current => Current; public void Dispose() => Enumerator.Dispose(); public T Current => didPeek ? peek : Enumerator.Current; #endregion public PeekEnumerator(IEnumerator enumerator) => Enumerator = enumerator ?? throw new ArgumentNullException(nameof(enumerator)); /// /// Fetch the next element, if not already performed. /// /// True/False that a Next element exists /// Advances the enumerator if Next has not been peeked already private bool TryFetchPeek() { if (!didPeek && (didPeek = Enumerator.MoveNext())) peek = Enumerator.Current; return didPeek; } /// /// Peeks to the next element /// /// Next element /// Throws an exception if no element exists public T Peek() { if (!TryFetchPeek()) throw new InvalidOperationException("Enumeration already finished."); return peek; } public T PeekOrDefault() { return !TryFetchPeek() ? default(T) : peek; } /// /// Checks if a Next element exists /// /// True/False that a Next element exists public bool PeekIsNext() { return TryFetchPeek(); } } }