NET 基于反射,泛型排序扩展类
ReflectionOrderExtend.cs

/// <summary> /// 泛型排序扩展类:运行时一个泛型一个实例 /// </summary> /// <typeparam name="T"></typeparam> public class ReflectionOrderExtend<T> { /// <summary> /// Key:Expression_PropertyTypeName_PropertyFieldName /// Value:表达式[x => x.Name] /// </summary> private readonly static Dictionary<string, dynamic> ExpressionDirctionary = new Dictionary<string, dynamic>(); /// <summary> /// 静态访问类只会访问一次 /// </summary> static ReflectionOrderExtend() { } /// <summary> /// 每次New都会访问 /// </summary> public ReflectionOrderExtend() { } /// <summary> /// 自定义排序 /// </summary> /// <param name="dbModelList"></param> /// <param name="orderbyList"></param> /// <returns></returns> public static IEnumerable<T> CustOrder(IEnumerable<T> dbModelList, List<string> orderbyList) { if (orderbyList.IsNullOrEmpty()) return dbModelList; var type = typeof(T); var count = orderbyList.Count(); IOrderedEnumerable<T> orderList = null; // 1.定义lamada的参数,型如我们常写的“x=>” ParameterExpression m_Parameter = Expression.Parameter(type, "x"); for (int i = 0; i < count; i++) { var orderBy = orderbyList[i].Split(' '); // 排序字段 var itemFieldName = orderBy[0]; // 严格区分大小写 var itemProperInfo = type.GetProperty(itemFieldName); if (itemProperInfo == null) continue; var itemType = itemProperInfo.PropertyType; // 排序方式,默认Asc:Asc | Desc var itemSort = orderBy.Length > 1 ? orderBy[1] : string.Empty; // 动态构建表达式 var lamada = BuilderLambda(type, m_Parameter, itemFieldName); switch (itemSort?.ToLower()) { case "desc": //if (i == 0) orderList = dbModelList.OrderByDescending(x => lamada); //else orderList = orderList.ThenByDescending(x => lamada); if (i == 0) orderList = dbModelList.OrderByDescending(x => lamada(x)); else orderList = orderList.ThenByDescending(x => lamada(x)); break; case "": case "asc": default: //if (i == 0) orderList = dbModelList.OrderBy(x => lamada); //else orderList = orderList.ThenBy(x => lamada); if (i == 0) orderList = dbModelList.OrderBy(x => lamada(x)); else orderList = orderList.ThenBy(x => lamada(x)); break; } } var newDbModelList = orderList.IsNullOrEmpty() ? dbModelList : orderList.ToList(); return newDbModelList; } /// <summary> /// 动态构建表达式 /// </summary> /// <param name="type"></param> /// <param name="m_Parameter"></param> /// <param name="itemFieldName"></param> /// <returns></returns> private static dynamic BuilderLambda(System.Type type, ParameterExpression m_Parameter, string itemFieldName) { // 缓存Key var itemKey = $"Expression_{type.Name}_{itemFieldName}"; dynamic lamada; if (ExpressionDirctionary.ContainsKey(itemKey)) { lamada = ExpressionDirctionary[itemKey]; } else { // 2.定义要使用lamada的属性成员(比如我们这里要对DTO_ORDER对象的ORDER_NO属性做筛选) MemberExpression member = Expression.PropertyOrField(m_Parameter, itemFieldName); // 3.转换为Expression表达式 x => x.XXX dynamic exprelamada = Expression.Lambda(member, m_Parameter); //5.将Expression表达式转换为Func委托,用于Where里面的参数 lamada = exprelamada.Compile(); ExpressionDirctionary.Add(itemKey, lamada); } return lamada; } }
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列:基于图像分类模型对图像进行分类
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现