I'm looking for a function to take a list of generic classes, and map it to different layout of datatable.
That means, I can't just directly map my class property names and values to grid, I need to convert it to the new values.
The solution that I came up with works, but it feels ... sloppy. Can anyone recommend a better way of doing it?
class Program
{
static void Main(string[] args)
{
var list = new List<InputClass>()
{
new InputClass {SomeField = "A", OtherField = 1},
new InputClass {SomeField = "B", OtherField = 2},
new InputClass {SomeField = "C", OtherField = 3},
new InputClass {SomeField = "D", OtherField = 4}
};
var dict = new Dictionary<string, Func<InputClass, object>>()
{
{"ColA", (f) => $"{f.SomeField}ABCD"},
{"ColB", (f) => DateTime.Now}
};
var dt = ToDataTable(list, dict);
Console.ReadKey();
}
public static DataTable ToDataTable<T>(List<T> list, Dictionary<string, Func<T, object>> columns) where T : class
{
var dt = new DataTable();
foreach (var key in columns.Keys)
{
var func = columns[key];
Type[] funcParams = (func.GetType()).GenericTypeArguments;
dt.Columns.Add(key, funcParams[1]);
}
foreach (var record in list)
{
var objects = new List<object>();
foreach (var key in columns.Keys)
{
objects.Add(columns[key](record));
}
dt.Rows.Add(objects.ToArray());
}
return dt;
}
}
class InputClass
{
public string SomeField { get; set; }
public int OtherField { get; set; }
}
(func.GetType()).GenericTypeArguments
. TheFunc
is always returning anobject
so why don't you just writedt.Columns.Add(key, typeof(object));
? \$\endgroup\$