0

In my project I am using Telerik RadGridView control, ItemSource of which is list of dynamic objects (derived from DynamicObject).
I was planning to use AggregateFunctions, like SumFunction, MinFunction, but it is crashing in columns, which are getting values from dynamic properties. If I am correct, it is because of Linq extensions, and not Telerik.
Is there any workaround for this issue?

Update
model class looks like this

public class SampleModel : DynamicObject
{
   // some properties
}   

Source is like:

 myGrid.ItemsSource = new List<SampleModel> { // some model items };

XAML is:

<telerik:RadGridView ShowColumnFooters="True" AutoGenerateColumns="False" x:Name="myGrid">
        <telerik:RadGridView.Columns>
            <telerik:GridViewDataColumn DataMemberBinding="{Binding p1}">
                <telerik:GridViewDataColumn.AggregateFunctions>
                    <telerik:SumFunction />
                </telerik:GridViewDataColumn.AggregateFunctions>
            </telerik:GridViewDataColumn>
        </telerik:RadGridView.Columns>
    </telerik:RadGridView>

Where p1 is dynamic property
Exception message is:
No generic method 'Sum' on type 'System.Linq.Enumerable' is compatible with the supplied type arguments and arguments. No type arguments should be provided if the method is non-generic.

4

1 回答 1

4

我通过创建自己的聚合函数并在其中手动构建表达式解决了这个问题(来源:Telerik 支持)。
Sum() 函数的代码是:

public class CustomSumFunction : EnumerableSelectorAggregateFunction
{
    protected override string AggregateMethodName
    {
        get { return "Sum"; }
    }

    protected override Type ExtensionMethodsType
    {
        get
        {
            return typeof(CustomAggregateFunctions);
        }
    }
}

public static class CustomAggregateFunctions
{
    public static TValue Sum<T, TValue>(IEnumerable<T> source, Func<T, TValue> selector)
    {

        return source.Select(selector).Aggregate((t1, t2) => 
            {
                Expression expr = Expression.Add(Expression.Constant(t1, t1.GetType()), Expression.Constant(t2, t2.GetType()));
                Expression conversion = Expression.Convert(expr, typeof(TValue));
                return Expression.Lambda<Func<TValue>>(conversion).Compile()();                    
            });
    }

    public static decimal? Sum<TSource>(IEnumerable<TSource> source, Func<TSource, decimal?> selector)
    {
        return source.Sum(selector);
    }

    public static decimal Sum<TSource>(IEnumerable<TSource> source, Func<TSource, decimal> selector)
    {
        return source.Sum(selector);
    }

    public static double? Sum<TSource>(IEnumerable<TSource> source, Func<TSource, double?> selector)
    {
        return source.Sum(selector);
    }

    public static double Sum<TSource>(IEnumerable<TSource> source, Func<TSource, double> selector)
    {
        return source.Sum(selector);
    }

    public static float? Sum<TSource>(IEnumerable<TSource> source, Func<TSource, float?> selector)
    {
        return source.Sum(selector);
    }

    public static float Sum<TSource>(IEnumerable<TSource> source, Func<TSource, float> selector)
    {
        return source.Sum(selector);
    }

    public static int? Sum<TSource>(IEnumerable<TSource> source, Func<TSource, int?> selector)
    {
        return source.Sum(selector);
    }

    public static int Sum<TSource>(IEnumerable<TSource> source, Func<TSource, int> selector)
    {
        return source.Sum(selector);
    }

    public static long? Sum<TSource>(IEnumerable<TSource> source, Func<TSource, long?> selector)
    {
        return source.Sum(selector);
    }

    public static long Sum<TSource>(IEnumerable<TSource> source, Func<TSource, long> selector)
    {
        return source.Sum(selector);
    }
}
于 2013-10-04T18:26:51.323 回答