質問

C#では、オブジェクトの列挙器からオブジェクトの配列を作成する最もエレガントな方法は何ですか?たとえば、この場合、BYTEを返すことができる列挙器があるので、これをBYTE []に変換したいと思います。

編集:列挙器を作成するコード:

IEnumerator<byte> enumerator = updDnsPacket.GetEnumerator();
役に立ちましたか?

解決

あなたが持っていると仮定します IENUMERABLEu003CT>, 、使用できます Enumerable.ToArray 拡張方法:

IEnumerable<byte> udpDnsPacket = /*...*/;

byte[] result = udpDnsPacket.ToArray();

他のヒント

さて、あなたが実際の列挙者を持っていると仮定すると(IEnumerator<byte>)、時間のループを使用できます。

var list = new List<byte>();
while(enumerator.MoveNext())
  list.Add(enumerator.Current);
var array = list.ToArray();

現実には、私は回したいと思っています IEnumerator<T>IEnumerable<T>:

public static class EnumeratorExtensions
{
    public static IEnumerable<T> ToEnumerable<T>(this IEnumerator<T> enumerator)
    {
      while(enumerator.MoveNext())
          yield return enumerator.Current;
    }
}

次に、配列を取得できます。

var array = enumerator.ToEnumerable().ToArray();

もちろん、これはすべて.NET 3.5以上を使用していると仮定しています。

あなたが持っているので IEnumerator<byte> そして、ではありません IEnumerable<byte>, 、linqを使用することはできません ToArray 方法。 ToArray です 拡張法 の上 IEnumerable<T>, 、オンではありません IEnumerator<T>.

拡張メソッドを作成することをお勧めします Enumerable.ToArray しかし、その後、列挙器の配列を作成する目的のために:

public T[] ToArray<T>(this IEnumerator<T> source)
{
    T[] array = null;
    int length = 0;
    T t;
    while (source.MoveNext())
    {
        t = source.Current();
        if (array == null)
        {
            array = new T[4];
        }
        else if (array.Length == length)
        {
            T[] destinationArray = new T[length * 2];
            Array.Copy(array, 0, destinationArray, 0, length);
            array = destinationArray;
        }
        array[length] = t;
        length++;
    }
    if (array.Length == length)
    {
        return array;
    }
    T[] destinationArray = new T[length];
    Array.Copy(array, 0, destinationArray, 0, length);
    return destinationArray;
}

何が起こるかは、アイテムごとに列挙者のアイテムを反復し、サイズが徐々に増加している配列に追加することです。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top