代码之家  ›  专栏  ›  技术社区  ›  Ritmo2k

使用LINQ表达式生成带有相关数据和条件的查询

  •  1
  • Ritmo2k  · 技术社区  · 6 年前

    我有以下回复 Name 在所有 MyParent 具有相关 MyChild 其中指定的字段(仅在运行时已知)是 true .

    这个示例可以工作,但是我确信有足够的空间来简化查询。测试用例删除了很多不相关的数据,比如元数据和导航属性。实际的数据存储是一个MSSQL数据库。是否可以避免组构造?

    using System;
    using System.Linq;
    using System.Linq.Expressions;
    
    public class MyParent
    {
        public int Id { get; set; }
        public string Name { get; set; }
        public bool Enabled { get; set; }
    }
    
    public class MyChild
    {
        public int Id { get; set; }
        public bool FieldA { get; set; }
        public bool FieldB { get; set; }
        public int MyParentId { get; set; }
    }
    
    class Program
    {
        static void Main()
        {
            var childA = new MyChild { Id = 0, FieldA = false, MyParentId = 0 };
            var parentA = new MyParent { Id = 0, Name = "John", Enabled = true };
            var childB = new MyChild { Id = 1, FieldA = true, MyParentId = 1 };
            var parentB = new MyParent { Id = 1, Name = "Jane", Enabled = true };
    
            var userField = "FieldA";
            var parents = new[] { parentA, parentB }.AsQueryable();
            var children = new[] { childA, childB }.AsQueryable();
    
            var parameter = Expression.Parameter(typeof(MyChild), "p");
            var property = Expression.Property(parameter, userField);
            var lambda = Expression.Lambda<Func<MyChild, bool>>(property, parameter);
    
            var query =
                from parent in parents
                join child in children on parent.Id equals child.MyParentId into grp
                from g in grp.AsQueryable().Select(lambda).Where(p => p)
                where parent.Enabled
                select parent.Name;
        }
    }
    
    1 回复  |  直到 6 年前
        1
  •  0
  •   Aldert    6 年前

    这将使用反射来完成这个技巧,不需要分组。

    static void Main()
        {
            var childA = new MyChild { Id = 0, FieldA = false, MyParentId = 0 };
            var parentA = new MyParent { Id = 0, Name = "John", Enabled = true };
            var childB = new MyChild { Id = 1, FieldA = true, MyParentId = 1 };
            var parentB = new MyParent { Id = 1, Name = "Jane", Enabled = true };
    
            var parents = new[] { parentA, parentB }.AsQueryable();
            var children = new[] { childA, childB }.AsQueryable();
    
            var userField = "FieldA";
    
            var childQuery = from child in children.Where(c => c.GetType().GetProperty(userField).GetValue(c).Equals(true)) select child;
    
            var query =
                from parent in parents
                join child in childQuery on parent.Id equals child.MyParentId
                where parent.Enabled
                select parent.Name;
        }