将OrderBy lambda函数作为参数

时间:2017-11-28 20:05:24

标签: c# linq lambda

我们说我的模型名称User包含一些属性NameAge。我想知道lambda函数的类型接受User并返回其中一个属性,以便lambda函数可以在OrderBy方法中使用。

using System;
using System.Linq;

public class User {
    public string Name { get; set; }
    public int Age { get; set; }
}

public class MainClass {
    static void Main() {

        var users = new User[] {
            new User { Name = "David", Age = 16 },
            new User { Name = "Charlie", Age = 29 },
            new User { Name = "Alice", Age = 15 },
            new User { Name = "Deanna", Age = 27 },
        }.AsQueryable();

        Write(GetAdultsBy(users, u => u.Name));
        Write(GetAdultsBy(users, u => u.Age));
    }

    private static IQueryable<User> GetAdultsBy(IQueryable<User> users, Func<User, object> order) {
        return users
            .Where(u => u.Age > 18)
            .OrderBy(order); // FAIL in ORDER BY
    }

    private static void Write(IQueryable<User> query) {
        var names = query.Select(u => u.Name);
        Console.WriteLine(string.Join(", ", names));
    }
}

运行this code时出现以下错误:

  

/tmp/997240133/main.cs(26,14):错误CS0266:无法隐式转换类型System.Linq.IOrderedEnumerable<User>' to System.Linq.IQueryable&#39;。存在显式转换(您是否错过了演员?)

但显式排序与Write(users.OrderBy(u => u.Age));一样可以正常工作。

那么Func<User, object> order参数的类型应该是什么?

2 个答案:

答案 0 :(得分:2)

您需要将private static IQueryable<User> GetAdultsBy()定义为通用函数,以匹配OrderBy&lt; &GT;被定义为。具体做法是:

private static IOrderedQueryable<User> GetAdultsBy<T>(
    IQueryable<User> source,
    Expression<Func<User, T>> order)

答案 1 :(得分:1)

要使用IQueryable,您需要传递表达式树(Expression<Func<...>>)。

表达式树在运行时对la​​mbda的内容进行编码,允许将其转换为SQL。