Reputation: 53
I have a requirement to convert LINQ to DataTable.
I stole the following Extension Method from StackOverflow:
public static DataTable ToDataTable<T>(this IEnumerable<T> items)
{
var tb = new DataTable(typeof(T).Name);
PropertyInfo[] props =
typeof(T).GetProperties(BindingFlags.Public
| BindingFlags.Instance);
foreach (var prop in props)
{
tb.Columns.Add(prop.Name, prop.PropertyType);
}
foreach (var item in items)
{
var values = new object[props.Length];
for (var i = 0; i < props.Length; i++)
{
values[i] = props[i].GetValue(item, null);
}
tb.Rows.Add(values);
}
return tb;
}
When the table contains null values it throws exception. (i.e)
DataSet does not support System.Nullable<>
Comission (Decimal type) column contains null value)
at
tb.Columns.Add(prop.Name, prop.PropertyType);
How to fix it?
Upvotes: 5
Views: 2533
Reputation: 388
You could check for null, and then store DBNull.Value as the value instead. There is an MSDN article about null values, that specifically calls out the lack of support for Nullable<> by Datasets.
Where you have
values[i] = props[i].GetValue(item, null);
make it
var value = props[i].GetValue(item, null);
values[i] = value ?? ((object)DBNull.Value);
Upvotes: 1
Reputation: 19263
Here's a pimped version:
public static DataTable ToDataTable<T>(this IEnumerable<T> items) {
DataTable table = new DataTable(typeof(T).Name);
PropertyInfo[] props = typeof(T).GetProperties(BindingFlags.Public | BindingFlags.Instance);
foreach (var prop in props) {
Type propType = prop.PropertyType;
// Is it a nullable type? Get the underlying type
if (propType.IsGenericType && propType.GetGenericTypeDefinition().Equals(typeof(Nullable<>)))
propType = new NullableConverter(propType).UnderlyingType;
table.Columns.Add(prop.Name, propType);
}
foreach (var item in items) {
var values = new object[props.Length];
for (var i = 0; i < props.Length; i++)
values[i] = props[i].GetValue(item, null);
table.Rows.Add(values);
}
return table;
}
Edit: Modified my code a bit, tested it, it works! :)
Upvotes: 5