سؤال

هل هناك طريقة جيدة للتعداد من خلال مجموعة فرعية فقط من مجموعة في C #؟ وهذا هو، لدي مجموعة من عدد كبير من الأشياء (قل، 1000)، ولكن أود التعداد من خلال العناصر فقط 250 - 340. هل هناك طريقة جيدة للحصول على عداد لمجموعة فرعية من المجموعة، دون باستخدام مجموعة أخرى؟

تحرير: يجب أن يكون قد ذكر أن هذا يستخدم .NET Framework 2.0.

هل كانت مفيدة؟

المحلول

حاول القيام بما يلي

var col = GetTheCollection();
var subset = col.Skip(250).Take(90);

أو أكثر عموما

public static IEnumerable<T> GetRange(this IEnumerable<T> source, int start, int end) {
  // Error checking removed
  return source.Skip(start).Take(end - start);
}

تعديل 2.0 الحل

public static IEnumerable<T> GetRange<T>(IEnumerable<T> source, int start, int end ) {
  using ( var e = source.GetEnumerator() ){ 
    var i = 0;
    while ( i < start && e.MoveNext() ) { i++; }
    while ( i < end && e.MoveNext() ) { 
      yield return e.Current;
      i++;
    }
  }      
}

IEnumerable<Foo> col = GetTheCollection();
IEnumerable<Foo> range = GetRange(col, 250, 340);

نصائح أخرى

أحب أن أبقيها بسيطة (إذا كنت لا تحتاج بالضرورة إلى العداد):

for (int i = 249; i < Math.Min(340, list.Count); i++)
{
    // do something with list[i]
}

تكييف رمز Jared الأصلي ل .NET 2.0:

IEnumerable<T> GetRange(IEnumerable<T> source, int start, int end)
{
    int i = 0;
    foreach (T item in source)
    {
        i++;
        if (i>end) yield break;
        if (i>start) yield return item;
    }
}

واستخدامها:

 foreach (T item in GetRange(MyCollection, 250, 340))
 {
     // do something
 }

تكييف رمز جاراد مرة أخرى، وستحصل لك طريقة Extention هذه المجموعة الفرعية التي يتم تعريفها بواسطة غرض, ، وليس الفهرس.

    //! Get subset of collection between \a start and \a end, inclusive
    //! Usage
    //! \code
    //! using ExtensionMethods;
    //! ...
    //! var subset = MyList.GetRange(firstItem, secondItem);
    //! \endcode
class ExtensionMethods
{
    public static IEnumerable<T> GetRange<T>(this IEnumerable<T> source, T start, T end)
    {
#if DEBUG
        if (source.ToList().IndexOf(start) > source.ToList().IndexOf(end))
            throw new ArgumentException("Start must be earlier in the enumerable than end, or both must be the same");
#endif
        yield return start;

        if (start.Equals(end))
            yield break;                                                    //start == end, so we are finished here

        using (var e = source.GetEnumerator())
        { 
            while (e.MoveNext() && !e.Current.Equals(start));               //skip until start                
            while (!e.Current.Equals(end) && e.MoveNext())                  //return items between start and end
                yield return e.Current;
        }
    }
}

قد تكون قادرا على القيام بشيء ما مع LinQ. الطريقة التي أود القيام بها هي وضع الكائنات في صفيف، ثم يمكنني اختيار العناصر التي أريد معالجةها بناء على معرف الصفيف.

إذا وجدت أنك بحاجة إلى القيام بمبلغ عادل من تقطيع وتسخين القوائم والمجموعات، فقد يستحق التسلق منحنى التعلم إلى مكتبة جمع C5 العامة.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top