Is it possible to put two Lambda expressions inside a single query? - c#

I was wondering if there is an easy way to place two Lambda expressions in a single (Linq/Where) query?
For example, I currently call a method with something like the following:
string testing = "blablabla";
if(testing == "" || testing == null)
I have tried a few combinations such as:
testing.Where(x => x == ("") || x=> x == null);
But the above doesn't work. I know I can set up a method that returns a predicate/bool, but, at the moment, I am interested in Lambdas and was just wondering how to achieve this.
Do I need to chain multiple Where methods, or is there a way to achieve multiple Lambdas?
(p.s. I know about IsNullOrEmpty, this is just the first example I could think of!)

You can always combine them to a single lambda.
testing.Where(x => x == null || x == ("") );

If you're looking for a general way to combine query conditions in arbitrary ways, you can use expression trees:
http://msdn.microsoft.com/en-us/library/bb882637.aspx

Related

Different treatment for single multiline parameter

I want to enforce the first parameter to be placed on a new line if there are several parameters and not all of them are placed on a single line
this is the setting for that: csharp_wrap_after_invocation_lpar = true
now in a case when there is a single parameter but it spans multiple lines e.g. a ternary expression or a lambda, I prefer it to start on the same line
.Select(r => r.Id == Id.None
? new Unload()
: new Load(r.Id));
instead of
.Select(
r => r.Id == Id.None
? new Unload()
: new Load(r.Id));
is there a way to achieve this?
I played around and was not able to find a setting for your desired behavior. Therefore I'd say it's not possible. But of course, you can ask JetBrains support.

Simplify conditional ternary expression in c#

I have a condition as shown below:
x.Customer == null ? false : x.Customer.CustomerData.IsSet
My IDE is saying to Simplify conditional ternary expression. Is there any other way to simplify this in dotnet? I recently started working with c# world it so kinda confuse on this.
Also can we also add a null check CustomerData too just like I have for Customer in a single line as well?
I tried like this -
Field("isSet", x => x.Customer?.CustomerData?.IsSet ?? false);
When I try this, it gives an error as -
An expression tree lambda may not contain conditional access
expression
The result of your expression is boolean so there's no need to write ternary operator. You can write it this way:
x.Customer != null && x.Customer.CustomerData.IsSet
Just try
bool result = x.Customer?.CustomerData?.IsSet ?? false
So if any of Customer or CutomerData is null, default will be false, otherwise IsSet will be returned.

How to compare inexact string values

I want to compare two string values which are not exact For example I want to compare Admin to Administrator, this should return true or should execute.
I tried contain which is not working
var prodcut = lstProducts.Where(i => i.Name.ToLower().Contains(appname.ToLower())).FirstOrDefault();
Above code not working if i.Name is 'Admin' and appname.ToLower() is 'Administrator'. It just return null but want it should detect values.
If you want to check it both ways so if A contains B OR if B contains A you can use the || operator (the OR operator) like so:
a.Contains(b) || b.Contains(a)
You've got the strings the wrong way around (you're looking for Adminstrator in Admin)
You can do the check both ways around like this:
lstProducts.Where(i =>
i.Name.ToLower().Contains(appname.ToLower()) ||
appname.ToLower().Contains(i.Name.ToLower())
).FirstOrDefault();
Or just compare the first few characters:
lstProducts.Where(i =>
i.Name.ToLower().SubString(0,5) == appname.ToLower().SubString(0,5))
).FirstOrDefault();
Fuzzy matching is actually quite a complicated subject but there's a lot of research into the topic.

How to evaluate a simple C# string

I have been reading up Expression trees, and I think this is a good example to use them, still I can't seem to grasp how this would be done.
I have a set of strings that I want evaluated, they are all of the type:
exp == exp , or exp != exp , or exp (<,>,>=,<=) exp if exp is Numerical Type.
The exp do not need to check if they are valid I am fine with them blowing up if they are not.
My issue is, how to I parse to get the actual obj.
I want to pass a string like these below
Owner.Property.Field == 3;
or
Owner.Field == 3;
or
Owner.Method(1) == true
And get if the evaluation is true or not. MY issue is how do I travel down the "path" on the left and get the value?
I implemented a version with Reflection and string parsing, that somehow does the work - except for when we are using a method, and honestly its not that performant at all. I want this to be as performant as possible can get, and if possible give me a small explanation of how the expression works , so I can learn.
You can use code generation libraries like CodeDOM or Roslyn to generate Func that will do the evaluation.
For example, in Roslyn you can create a Session and set an object containing Owner as the Host object of the Session. than you can generate the code in the Session as you wish like the following:
Session session = ScriptEngine.CreateSession(objectContainingOwnerAsProperty);
bool result = session.Execute<bool>("Owner.Field == 8");
Now result will contain the evaluation result for your string without reflection nor string analysis.

Conditional Statement Checking Null

I'm trying to figure out how to have a short, one line conditional statement.
If this date is not null, add the filter to the current list of filters:
fromDt ?? filters.Add(FilterType.DateFrom, fromDt);
Is there a way to do this? I know I could do..
(fromDt != null) ? "something" : "something_else", but I don't need the 'else', and would really like to just use the ?? operator for null checking.
What's wrong with this?
if (fromDt != null) filters.Add(FilterType.DateFrom, fromDt);
First and foremost, your code should be readable. Even if your ?? code works, I wouldn't know what it does on first glimpse.
The code you are attempting makes your code very difficult to read. Like BrokenGlass said, you are trading clarity for raw character count.
This is the only "one line" solution C# supports.
if (fromDt != null) filters.Add(FilterType.DateFrom, fromDt);
But I encourage everyone to expand this to at least two lines (my preference is four with the braces).
Purpose of the solution aside, following one-liner might give you end result you want while using ??. Do not try this at home though.
filters.Add(FilterType.DateFrom, fromDt ?? DateTime.MinValue)
The idea is to set DateFrom to min possible value, essentially adding an open filter.

Categories