using DynamicSort;
using Microsoft.EntityFrameworkCore;

List<StudnetEntity> studentList = new List<StudnetEntity>()
{
    new StudnetEntity(){ Name = "Chen", Age = 28},
    new StudnetEntity(){ Name = "Wang", Age = 29}
};

//排序属性可以在编译时确定
List<StudnetEntity> staticOrderList = studentList.OrderByDescending(a => a.Age).ToList();

//Entity Framework的动态排序
//排序属性可以在运行时确定。
//直接使用报错The EF.Property<T> method may only be used within Entity Framework LINQ,
//必须使用DbContext,也就是Entity Framework的
//例如DbContext.Entity.OrderByDescending(e => EF.Property<Object>(e, sortParam)).ToList();
string sortParam = "Age";
//List<StudnetEntity> dynamicOrderList = studentList.OrderByDescending(e => EF.Property<Object>(e, sortParam)).ToList();

string sortParamValue = "Age";
List<StudnetEntity> newdynamicOrderList = studentList.AsQueryable().OrderByDynamic(sortParamValue, true).ToList();

newdynamicOrderList.ForEach(a =>
{
    Console.WriteLine(a.Name + a.Age);
});

public class StudnetEntity
{
    public string Name { get; set; }
    public int Age { get; set; }
}
using System.Linq.Expressions;

namespace DynamicSort
{
    public static class SortHelper
    {
        public static IQueryable<T> OrderByDynamic<T>(this IQueryable<T> query, string sortParam, bool desc)
        {
            // 检查 sortParam 是否为空或空字符串
            if (string.IsNullOrEmpty(sortParam))
            {
                throw new ArgumentException("Sort parameter cannot be null or empty", nameof(sortParam));
            }
            // 获取 T 类型的信息
            var entityType = typeof(T);
            // 尝试获取指定名称的属性
            var property = entityType.GetProperty(sortParam);
            // 如果属性不存在,则抛出异常
            if (property == null)
            {
                throw new ArgumentException($"Property '{sortParam}' not found on type '{entityType.Name}'");
            }
            // 创建一个参数表达式,代表单个实体实例
            var parameter = Expression.Parameter(entityType, "e");
            // 创建属性访问表达式,代表对该属性的访问
            var propertyAccess = Expression.MakeMemberAccess(parameter, property);
            // 创建 lambda 表达式,表示对实体的属性访问
            var orderByExpression = Expression.Lambda(propertyAccess, parameter);
            // 根据 desc 参数决定使用 OrderBy 还是 OrderByDescending
            string methodName = desc ? "OrderByDescending" : "OrderBy";
            // 构建排序方法调用表达式
            var resultExpression = Expression.Call(
                typeof(Queryable),                 // 静态类 Queryable
                methodName,                        // 方法名:OrderBy 或 OrderByDescending
                new Type[] { entityType, property.PropertyType },  // 泛型参数
                query.Expression,                  // 原始查询表达式
                Expression.Quote(orderByExpression)  // lambda 表达式
            );
            // 创建并返回新的排序后的查询
            return query.Provider.CreateQuery<T>(resultExpression);
        }
    }
}

 

posted on 2024-05-17 17:29  HuairongChen  阅读(17)  评论(0编辑  收藏  举报