Reputation: 3109
I have a collection being returned by a web service. A property of this collection is "StatusCode" which is a string value that can be anywhere from 0 to 5 (don't ask me why it was set up as a string... I didn't schema this). Initially I was going to use LINQ to filter this, then realized that was stupid (why return 100% of the records when I need 20%) and I parameterized my Stored Proc to do this for me.
In any case, I wrote a LINQ query that worked, but for curiosity sake, I imagine there's a better way to do it:
var wo = from w in workOrders
where w.StatusCode == "0"
|| w.StatusCode == "1"
|| w.StatusCode == "2"
select w;
Any suggestions? Correct answer goes to most thorough answer - including either documentation, best practice, etc...
Upvotes: 1
Views: 7671
Reputation: 58293
I recently wrote a blog post about a method using extension methods and params.
By adding this extension method to your code:
public static bool IsIn<T>(this T source, params T[] values)
{
return values.Contains(source);
}
you can perform your search like this:
var wo = from w in workOrders
where w.StatusCode.IsIn("0", "1", "2")
select w;
It works on any type (as long as you create a good equals method). Any value type for sure.
Upvotes: 2
Reputation: 9052
Your method is ok. I don't believe parsing or lookup collection is neccessary for 3 string values (however it certainly isn't wrong). With parsing I'd be afraid of empty strings or nulls (even tho we know that there should only be strings 0-5).
If you are anticipating filtering like this on more places you should probably create method (or extension) on WorkOrder that would determine current state more expressively like
public static bool IsNotCompleted(this WorkOrder workOrder)
{
return workOrder.Status == "0" || workOrder.Status == "1" || workOrder.Status == "2";
}
and then
var wo = from o in workOrders where o.IsNotCompleted() select o;
or (I personally prefer this sytaxe)
var wo = workOrders.Where(o => o.IsNotCompleted());
Using extension to describe state like this will increase readability and it will be much easier to add/remove status codes in future.
Upvotes: 1
Reputation: 29163
You could define an IsIn()
generic Extension Method:
public static bool IsIn<T>(this T value, params T[] values)
{
return values.Contains(value);
}
Then you could write your query like this:
var wo = from q in workOrders where w.IsIn("1","2","3") select w;
Upvotes: 1
Reputation: 225269
var wo = from q in workOrders where int.Parse(w.StatusCode) < 3 select w;
Is a cleaner way to do the LINQ query, at least.
Upvotes: 2
Reputation: 18257
var wo = from w in workOrders
where new[]{"0", "1", "2"}.Contains(w.StatusCode)
select w;
BTW, if you were using an ORM, you could do it in LINQ (like the above) and only pull the 20% from the database ;)
Upvotes: 2