views:

100

answers:

4

I want to generate dynamic query to check manage the where clause with number of parameters available...if some parameter is null i don't want to include it in the where clause

var test = from p in _db.test
           where if(str1 != null){p.test == str} else i dnt wanna check p.test

I have around 14 parameters for the where clause

need help, thanks

+4  A: 

You can do it in steps:

// set up the "main query"
var test = from p in _db.test select _db.test;
// if str1 is not null, add a where-condition
if(str1 != null)
{
    test = test.Where(p => p.test == str);
}
Fredrik Mörk
Note that sometimes you won't be able to use `var` here because the compile-time type of `_db.test` may be more specific than the `IEnumerable<T>` returned by `Where`. Also note that you can't use just "from p in _db.test" on its own ;)
Jon Skeet
i have around 14 parameter for the where clause..does it it mean i have to check for every parameter...is there any way to make this query dynamic, what if more than one parameter is null :)
Hasan
@Jon: ha, I was a bit distracted when writing so I forgot the select. Thanks for pointing it out.
Fredrik Mörk
@Hasan: there is no magic bullet. If you want to include certain parameters in the query based on certain conditions, you will need to check those conditions in some way.
Fredrik Mörk
@Jon that means I have to make combination of 14 pairs...thats huge
Hasan
@Hasan, no you just have 14 if statements. I do this all the time for optional filter parameters.
Ryan
+1  A: 

In addition to @Fredrik's answer, you can also use the short-circuit rules when evaluating boolean expressions like so:

var test = from p in _db.test
           where str1 == null || p.test == str1;

Edit If you have lots of strings to test, (str1, str2, etc...) then you can use the following, which will be translated to an SQL IN clause:

var strings = new List<string>();
if (str1 != null) strings.Add(str1);
if (str2 != null) strings.Add(str2);
if (str3 != null) strings.Add(str3);
...

var test = from p in _db.test
           where strings.Contains(p.test);

It's even easier if your strings are already in a collection (which, if you've got 14 of them, I assume they would be...)

Dean Harding
If str1 == null I dont wanna check p.test...and i have 14 strings
Hasan
any suggestions?
Hasan
@Hasan: that is exactly what @Dean is writing: if `str == null`, `p.test == str1` will not be checked.
Fredrik Mörk
+1  A: 

Consider param1 and param2 are the parameters. Your query should be as under:

string param1 = "Value1";
string param2 = "Value2";

var q = from bal in context.FxBalanceDetails
        where (string.IsNullOrEmpty(param1) || bal.Column1 == param1)
               && (string.IsNullOrEmpty(param2) || bal.Column2 == param2)
        select bal;

This will ensure that the where clause gets applied for the particular parameter only when it is not null.

Rashmi Pandit
I'd be careful doing everything in one where clause. I think if your linq provider (EF, L2S, NH, etc) can't convert something inside the where clause to SQL you'll probably end up pulling the entire table into memory.
Ryan
Yeah, I understand. LINQ can generate pretty nasty SQL sometimes. I've used this method in SPs very successfully though.
Rashmi Pandit
A: 

Do you check the strings against the same Field of the entity? If so you can write something like:

var strings = new[] { "foo", "bar", "ok", "", null };
var query = dataContext.YourTable.AsQueryable();
query = strings.Where(s => !string.IsNullOrEmpty(s))
       .ToList()
       .Aggregate(query, (q, s) => q.Where(e => e.YourField == s));

EDIT: The previous solution is overcomplicated:

var strings = new[] { "foo", "bar", "ok", "", null }.Where(s => !string.IsNullOrEmpty(s))
       .ToList();
var query = dataContext.YourTable.Where(e => strings.Contains(e.YourField));
Guillaume86