IEnumerable <IEnumerable>> и метод расширения - PullRequest
0 голосов
/ 12 октября 2018

Мне было интересно, может ли кто-нибудь помочь мне понять следующее поведение.В следующем коде я создаю экземпляр CustomObject, который содержит одно свойство типа IEnumerable<IEnunumerable>>.

. У меня также есть метод расширения для IEnumerable<T>, называемый AsDataTable.

public class CustomObject
{
public IEnumerable<IEnumerable> Collection {get;set;}
}


public static class ExtensionMethods
{

public static bool AsDataTable<T>(this IEnumerable<T> list)

{
    Console.Write("In extension method");
    return default(bool);
}
}

void Main()
{

    var ttObject = new CustomObject()
    {
        Collection = new List<IEnumerable>
        {
            new List<int>{1,2,3},
            new [] {new{A="abc",B="def"}}
        } 
    };
    var dummy = new []{new {a='r'}}.AsDataTable();

    foreach(var item in ttObject.Collection)
    {
        var temp = item.AsDataTable();
        Console.WriteLine($"Item is IEnumerable : {item is IEnumerable}");
    }
}

Что заставляет меня задуматься, работает ли следующая строка кода (или, скорее, компилируется)

var dummy = new []{new {a='r',b='3'}}.AsDataTable();

, когда я зацикливаюсь над свойством Collection CustomObject, а затем делаю то же самое, что и не 'я не могу его скомпилировать.

var temp = item.AsDataTable(); // this doesn't work

Любопытно, что следующая строка возвращает истинное подтверждение того, что 'item' действительно IEnumerable.

 Console.WriteLine($"Item is IEnumerable : {item is IEnumerable}");

Я думаю, это потому, что метод расширения написанпо общей версии IEnumerable<T>, но как же тогда она работает над массивом анонимного типа (за пределами CustomObject).

1 Ответ

0 голосов
/ 12 октября 2018

IEnumerable<T> реализует IEnumerable, а не наоборот.

Путем небольшого взлома во время выполнения, SomeType[] фактически реализует IEnumerable<SomeType>.С другой стороны, IEnumerable нет - и разрешение перегрузки выполняется во время компиляции, поэтому компилятор даже не подозревает, что ваши IEnumerable элементы в коллекции на самом деле также реализуют IEnumerable<int>.

Есливам нужно работать с IEnumerable, вы должны использовать это в своем методе расширения.

...