简体   繁体   中英

dynamic conditions in where clause of Linq c#

So I have a class:

public class Snowman
{

    public Snowman(string Appearance, string Colour, string Name)
    {
        this.AppearanceProp = Appearance;
        this.ColourProp = Colour;
        this.NameProp = Name;
    }
    public string AppearanceProp { get; set; }
    public string ColourProp { get; set; }

    public string NameProp
    { get; set; }
}

a list of snowmen objects:

List<Snowman> snowmen = new List<Snowman>()
{
    new Snowman("Proud", "White", "Jose"),
    new Snowman("Dreamer", "Silver", "Mark"),
    new Snowman("Dreamer", "Silver", "James"),
    new Snowman("Jaded", "White", "Jerry"),
    new Snowman("Joyous", "White", "Mark"),
    new Snowman("Joyous", "White", "Jose"),
    new Snowman("Joyous", "White", "James")
};

and a list of columns I want to filter the list of snowmen (the list updates dynamically at runtime):

var Column1 = "Appearance";
var Column2 = "Colour";
string Column3 = null;

so I should be able to dynamically filter using a dynamic linq with a dynamic where clause, something like this:

var chosenOnes = snowmen
    .Where(a =>
           Column1 != null ? a.GetType().GetProperty(Column1 + "Prop").GetValue(a, null).ToString() == values[i]  &&
           Column2 != null ? a.GetType().GetProperty(Column1 + "Prop").GetValue(a, null).ToString() == values[i+1] 
                );

This gives a syntax error,

expecting:

Not sure what I am missing

values is:

List<string> values = new List<string>() { "joyous", "white" };
var chosenOnes = snowmen
    .Where(a =>
        (Column1 == null || a.GetType().GetProperty(Column1 + "Prop").GetValue(a, null).ToString() == values[i])
        && (Column2 == null || a.GetType().GetProperty(Column2 + "Prop").GetValue(a, null).ToString() == values[i+1])
        && (Column3 == null || GetType().GetProperty(Column3 + "Prop").GetValue(a, null).ToString() == values[i+2])
    );

...or use collections to DRY this up:

var filters = new Dictionary<string, object> 
{
    { "Appearance", "Joyous" },
    { "Colour",     "White" }
};

var chosenOnes = snowmen;
foreach(var filter in filters)
{
    chosenOnes = chosenOnes.Where(a => 
        a.GetType()
         .GetProperty(filter.Key + "Prop")
         .GetValue(a, null) == filter.Value
    );
}

If I'm understanding the question correctly, you can do this:

var chosenOnes = snowmen;

if (Column1 != null)
    chosenOnes = chosenOnes.Where(a => a.GetType().GetProperty(Column1 + "Prop").GetValue(a, null).ToString() == values[i]);

if (Column2 != null)
    chosenOnes = chosenOnes.Where(a => a.GetType().GetProperty(Column2 + "Prop").GetValue(a, null).ToString() == values[i+1]);

if (Column3 != null)
    chosenOnes = chosenOnes.Where(a => a.GetType().GetProperty(Column3 + "Prop").GetValue(a, null).ToString() == values[i+2]);

Just apply the Where clauses for each column if they aren't null .

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM