Search code examples
c#linqlinq-to-dataset

DataTableExtensions.AsEnumerable() throws InvalidCastException


I'm using the DataTableExtensions.AsEnumerable method to create a List . The following code is throwing an InvalidCastException:

SaleDiscount = (i.Field<decimal>("OnSalePercentAdjustment") * i.Field<decimal>("Price")), 

I don't have to use LINQ, With a few more keystrokes I can work through the data table with a foreach loop:

i.Price = Convert.ToDecimal(row["Price"]);
var saleDiscount = Convert.ToDecimal(row["SaleDiscount "]);
i.SalePrice = i.Price - (i.Price * saleDiscount );
i.SaleDiscount = i.Price - i.SalePrice;

Just curious, how can I fix the LINQ? And wondering whether using LINQ here delivers any advantages over some saved keystrokes.


Solution

  • You get cast exceptions in one case and no exceptions in the other because Convert.ToDecimal is a lot more lenient than a simple cast. Cast exception indicates that the underlying field is not a decimal, but it has a type that can be easily converted to decimal.

    To use Convert.ToDecimal inside LINQ query, change your code as follows:

    SaleDiscount = (
               Convert.ToDecimal(i.Field<object>("OnSalePercentAdjustment")) *
               Convert.ToDecimal(i.Field<object>("Price"))), 
    

    Alternatively, you could figure out the correct type, use Field<correct-type>(...) to read it, and then do the cast to decimal.