User selection highlighting combining two classes

I have two classes (or models) that have some common properties. For instance:

public class Model1
{
    public int Common1 { get; set; }
    public int Common2 { get; set; }
    public int Prop11 { get; set; }
    public int Prop12 { get; set; }
}

public class Model2
{
    public int Common1 { get; set; }
    public int Common2 { get; set; }
    public int Prop21 { get; set; }
    public int Prop22 { get; set; }
}

I need to write a method that can accept an element selector expression, where the element to select can come from either of two models. Here is what I mean:

public List<T> GetAnon<T>(Expression<Func<??, T>> selector) // <-- intriguing part
{
    // codes to extract property names from selector and create the return object of type T
}

// And this is an example usage of the method
// At this point, I don't know which model Common1, Prop11 or Prop21 belongs to
var anonObj = GetAnon(m => new { m.Common1, m.Prop11, m.Prop21 });
// anonObj = { Common1 = VALUE_1, Prop11 = VALUE_2, Prop21 = VALUE_3 }

Note that the transmitted selectorselects both from Model1and from Model2.

My current solution: Create a model with common properties, such Modelas c Model1and Model2inherit, Modelwith the rest of the properties in separate models. Then create another model, say TempModel, which inherits Modeland adds non-common properties to it. For instance:

public class Model
{
    public int Common1 { get; set; }
    public int Common2 { get; set; }
}

public class Model1 : Model
{
    public int Prop11 { get; set; }
    public int Prop12 { get; set; }
}

public class Model2
{
    public int Prop21 { get; set; }
    public int Prop22 { get; set; }
}

public class TempModel : Model
{
    public int Prop11 { get; set; }
    public int Prop12 { get; set; }
    public int Prop21 { get; set; }
    public int Prop22 { get; set; }
}

// Finally, first type parameter can be TempModel
public List<T> GetAnon<T>(Expression<Func<TempModel, T>> selector)
{
    // codes to extract property names from selector and create the return object of type T
}

, Model1 Model2 , , TempModel, , , , intellisense.

? , #, .

Edit:

, ( , ). T GetAnon(). , ( SQL). , . , , , , , .

+4
2

, - :

public List<T> GetAnon<T>(Expression<Func<Model1, Model2, T>> selector) {

}

, ( ), , , , , ( , , , ).

:

var propNames = GetAnon((m1, m2) => new { m1.Common1, m1.Prop11, m2.Prop21 });
+1

, . , , , . nameof.

public List<string> GetMemberNames<T1, T2>(IEnumerable<string> propNames)
{
    var commonProps = (from pn in propNames
                       where
                       typeof(T1).GetProperties(BindingFlags.Instance | BindingFlags.Public)
                                 .Any(p => p.Name == pn) ||
                       typeof(T2).GetProperties(BindingFlags.Instance | BindingFlags.Public)
                                 .Any(p => p.Name == pn)
                       select pn).ToList();

    return commonProps;
}

:

var cp = GetMemberNames<Model1, Model2>(new[] 
                        { nameof(Model1.Common1),   
                          nameof(Model2.Common2), 
                          nameof(Model1.Prop11), 
                          nameof(Model2.Prop21),
                          "SomeUnknownProperty", 
                        });

, .

:

enter image description here

+2
source

Source: https://habr.com/ru/post/1694112/


All Articles