У меня есть класс Exporter, у которого есть универсальный метод, который принимает IEnumerable<T>
и создает документ экспорта, перечисляя значения его свойств с помощью отражения:
public class Exporter
{
public string Export<T>(IEnumerable<T> enumerable)
{
//Implementation omitted
}
}
Из-за вывода универсального типа я могу предоставитьэто с анонимным типом коллекции.Обратите внимание на отсутствие универсального параметра в вызове метода ниже:
string fooString =
new Exporter().Export(new List<Foo>()
{
new Foo() {Name = "cats", NumberOfHams = 1},
new Foo() {Name = "dogs", NumberOfHams = 8}
}
.Select(x => new { TwiceTheHams = x.NumberOfHams * 2 }));
Мы все любим C # 3.Однако я хотел бы адаптировать этот класс так, чтобы я мог ввести больше информации о столбцах в документе экспорта, например, о ширине.
Я создал новый метод в классе экспорта, который выглядит следующим образом:
public string Export<T>(IEnumerable<T> enumerable, IEnumerable<ColumnDetails<T>> columnDetails)
{
//Implementation omitted
}
В идеале синтаксис должен быть таким, где foos
имеет тип IEnumerable<Foo>
:
fooString = new Exporter().Export(foos,
new List<ColumnDetails<Foo>>
{
new ColumnDetails<Foo>(x => x.Name, 12),
new ColumnDetails<Foo>(x => x.NumberOfHams, 4),
});
Однако, когда я вызываю новую перегрузку Export()
, как указано выше, вывод универсального типа не кажется достаточно умным, чтобы сделать вывод, что универсальный параметр T
для ColumnDetails<T>
долженбыть таким же, как универсальный параметр T
для IEnumerable
.Это означает, что я должен указать List<ColumnDetails<Foo>>
в качестве параметра, и поэтому я не могу использовать это с анонимными коллекциями.
Я действительно новичок в обобщениях и выводе типов.Возможно ли то, что я пытаюсь сделать?Нужно ли как-то реструктурировать код?
Редактировать: это то, что я не могу сделать, потому что Visual Studio нужен универсальный параметр для ColumnDetails, которого у меня нет:
fooString = new Exporter().Export(foos.Select(x => new {TwiceTheHams = x.NumberOfHams * 2}),
new List<ColumnDetails>
{
new ColumnDetails(x => x.TwiceTheHams, 12)
});