Alternative IEnumerable <T> .Skip (1) .Take (1) .Single ()

I have a difficult time with an seemingly easy and embarrassing problem. All I want is the next element in IEnumberable without using Skip (1) .Take (1) .Single (). This example illustrates the main problem.

private char _nextChar;
private IEnumerable<char> getAlphabet()
{
    yield return 'A';
    yield return 'B';
    yield return 'C';
}
public void sortAlphabet()
{
     foreach (char alpha in getAlphabet())
     {
         switch (alpha)
         {
             case 'A':  //When A pops up, I want to get the next element, ie 'B'
                 _nextChar = getAlphabet().Skip(1).Take(1).Single();
                 break;
             case 'B': //When B pops up, I want 'C' etc
                 _nextChar = getAlphabet().Skip(1).Take(1).Single();
                 break;
         }
     }
}

Besides ugliness, this example works. But let's say that IEnumerable contained 2 million elements, then the LINQ statement forces the program to perform unbearably slow work. I want it simply. I just need the next element in IEnumberable <>. All my problems will be solved if a function such as:

_nextChar = getAlphabet().moveNext() //or getNext()

, // , . , 2 , "money = 324", "" "324" IEnumberable, "", , 324". ( ?: D .)

+5
6

, , :

_nextChar = getAlphabet().moveNext() //or getNext()

. IEnumerator<T>, IEnumerable<T>!

private char _nextChar;
private IEnumerable<char> getAlphabet()
{
    yield return 'A';
    yield return 'B';
    yield return 'C';
}

public void sortAlphabet()
{
    using (var enumerator = getAlphabet().GetEnumerator())
    {
        while (enumerator.MoveNext())
        {
            char alpha = enumerator.Current;
            switch (alpha)
            {
                case 'A':
                    if (enumerator.MoveNext())
                    {
                        _nextChar = enumerator.Currrent;
                    }
                    else
                    {
                        // You decide what to do in this case.
                    }
                    break;
                case 'B':
                    // etc.
                    break;
            }
        }
    }
}

. , IEnumerable<char>, IList<char>? , , , , , getAlphabet ( - , ElementAt, , ).

, , :

private char _nextChar;
private IList<char> getAlphabet()
{
    return Array.AsReadOnly(new[] { 'A', 'B', 'C' });
}

public void sortAlphabet()
{
    IList<char> alphabet = getAlphabet();
    for (int i = 0; i < alphabet.Count - 1; ++i)
    {
        char alpha = alphabet[i];
        switch (alpha)
        {
            case 'A':
                _nextChar = alphabet[i + 1];
                break;
            case 'B':
                // etc.
                break;
        }
    }
}

?

+13

, :

    public void sortAlphabet() {
        using (var enu = getAlphabet().GetEnumerator()) {
            while (enu.MoveNext()) {
                switch (enu.Current) {
                    case 'A':
                        enu.MoveNext();
                        _nextChar = enu.Current;
                        break;
                }
            }
        }
    }

, , , , .

+4

, MoveNext(), IEnumerator<T>, IEnumerable<T>.GetEnumerator(). , MoveNext() Current "".

, foreach getAlphabet(), , :

public static IEnumerable<T[]> InPairsOfTwo<T>(this IEnumerable<T> enumerable)
{
    if (enumerable.Count() < 2) throw new ArgumentException("...");

    T lastItem = default(T);
    bool isNotFirstIteration = false;

    foreach (T item in enumerable)
    {
        if (isNotFirstIteration)
        {
            yield return new T[] { lastItem, item };
        }
        else
        {
            isNotFirstIteration = true;
        }
        lastItem = item;
    }
}

:

foreach (char[] letterPair in getAlphabet().InPairsOfTwo())
{
    char currentLetter = letterPair[0],
         nextLetter    = letterPair[1];        

    Console.WriteLine("#  {0}, {1}", currentLetter, nextLetter);
}

:

#  A, B
#  B, C

( , , , ! , , , . , , .)

+1

, . , , . , , , . .

enum State
{
    Scan,
    SaveAndExit
};

public void SortAlphabet()
{
    State state = State.Scan; // initialize

    foreach(char c in getAlphabet())
    {
        switch (state):
        {
            case State.Scan:
                if (c == 'A' ||
                    c == 'B')
                    state = State.SaveAndExit;
                break;
            case State.SaveAndExit:
                return (c);
                break;
        }
    }
}
0

'B' , getAlphabet(), IEnumerable.

, , , . MoveNext , , .

0

.NET 4.0, , , :

var alphabet = getAlphabet();
var offByOneAlphabet = alphabet.Skip(1);

foreach (var pair in alphabet.Zip(offByOneAlphabet, (a, b) => Tuple.Create(a, b)))
    Console.WriteLine("Letter: {0}, Next: {1}", pair.Item1, pair.Item2);

// prints:
//    Letter: A, Next: B
//    Letter: B, Next: C

- , .NET 4.0, Zip Tuple.

0

All Articles