If I want to generate the query (month(created) = 1 and year(created) = 2010) or (month(modified) = 1 and year(modified) = 2010) with linq, how would I go about it?
I have o.Created.Value.Month == month && o.Created.Value.Year == year. If I do (o.Created.Value.Month == month && o.Created.Value.Year == year) || (o.Modified.Value.Month == month && o.Modified.Value.Year == year) wouldn't the parenthesis just be ignored?
No, the parentheses won't be ignored by LINQ - they're important to indicate the logic. They're effectively present in the expression tree, in that you'll end up with an "OR" expression with two subexpressions each of which is an "AND" expression.
The query you've given should be fine - have you tried it, and checked the resulting SQL?
Related
I am trying to simplify a C# method that includes the following query:
var matchingDeviceKeys =
from dev in data.Elements("Key1")
where dev.Element("Key2").Element("Key3").Element("VendorID").Value == device.Vendor &&
dev.Element("Key2").Element("Key3").Element("ProductType").Value == device.ProductType &&
dev.Element("Key2").Element("Key3").Element("ProductCode").Value == device.ProductCode
from rev in dev.Element("Key2").Element("Key3").Element("Key4").Elements("MajorRev")
where rev.Attribute("Number").Value == device.MajorRevision &&
rev.Attribute("DefaultMinorRev").Value == device.MinorRevision.ToString(CultureInfo.InvariantCulture)
select dev.Element("Key6").Element("Key7").Element("Key8");
The "rev" target for the second from clause is never used in the select line, making me wonder if that entire second from clause is doing anything. If it is doing something, what is it doing?
My apologies for obfuscating the element names. I have to be careful in sharing proprietary code.
I have a Linq query that works with various Where clause additions.
But I also want to return the SingleDate for an Event where it is today or tomorrow.
Dances_Moderated = Dances_Moderated
.Where(x => x.SingleDate == DateTime.Today)
&& (x => x.SingleDate == DateTime.Today.AddDays(1))
.ToList();
The code after the && is underlined in red, and the error says:
CS0023: Operator '.' cannot be applied to operand of type 'lambda expression'
You should use || (or) instead of && (and): x.SingleDate.Date should be either Today or tomorrow. I've added .Date in order to be on the safe side of the road: when we use == we want to compare dates only, not time parts.
Dances_Moderated = Dances_Moderated
.Where(x => x.SingleDate.Date == DateTime.Today ||
x.SingleDate.Date == DateTime.Today.AddDays(1))
.ToList();
You have couple of errors in your code:
First: Syntax error,
Second: Business error. Your SingleDate never gonna equal to datetime.now. You should use greater and less operator to do that.
Your code should be like this:
Dances_Moderated = Dances_Moderated.Where(x => x.SingleDate >= DateTime.Today && x.SingleDate <= DateTime.Today.AddDays(1)).ToList();
I have the following code:
DateTime timeStamp = Convert.ToDateTime(Request.QueryString["TimeStamp"]);
var result = (from rs in db.VRec
where
rs.TimeStamp == timeStamp &&
rs.Fixure == wFixture
select rs).ToList();
The result shows 0 even though the correct timeStamp is passed.
If I remove the part where I do the TimeStamp comparison:
rs.TimeStamp == timeStamp
The code works fine.
Any idea on why the datetime comparison may not be working?
DateTime has a pretty fine resolution - likely you are comparing timestamps that only differ in milliseconds, which will fail. You probably want something like:
DateTime now = DateTime.Now;
DateTime then = now.Add(TimeSpan.FromMilliseconds(1));
const int EPSILON_MS = 10;
if(now.Subtract(then).TotalMilliseconds < EPSILON_MS)
{
Console.WriteLine("More or less equal!");
}
Linq converts DateTime arguments to DateTime2 in the sql query executed.
That is, when you do the comparison the actual sql executed will compare a DateTime to a DateTime2. This comparison will "cast" the DateTime to a DateTime2 and the millisecond part will be expanded to a greater resolution (in an odd way in my opinion, please enlighten me).
Try to execute the following sql:
declare #d1 datetime = '2016-08-24 06:53:01.383'
declare #d2 datetime2 = '2016-08-24 06:53:01.383'
declare #d3 datetime2 = #d1
select #d1 as 'd1', #d2 'd2', #d3 'converted'
select (case when (#d1 = #d2) then 'True' else 'False' end) as 'Equal',
(case when (#d1 > #d2) then 'True' else 'False' end) as 'd1 greatest'
From the question, I do not know if you want to compare the date with time or only the date part. If you only want to compare date then following would work
var result = (from rs in db.VRec
where
rs.TimeStamp.Date == timeStamp.Date &&
rs.Fixure == wFixture
select rs).ToList();
Since you are using some reference to db, it gives me a feeling that you are fetching your records from database (which ORM you are using is not obvious from the question or tags). Assuming that you are using Entity framework the above query will fail with exception that .Date has no direct translation to sql. If so you can rewrite the query as following to make it work.
var result = (from rs in db.VRec
where
rs.TimeStamp.Day == timeStamp.Day &&
rs.TimeStamp.Month == timeStamp.Month &&
rs.TimeStamp.Year == timeStamp.Year &&
rs.Fixure == wFixture
select rs).ToList();
The benefit of this approach is that you can compare properties to arbitrary deep level i.e you can compare Hours, Minutes,Seconds etc. in your query. The second query is tested in Entity framework 5.
I have a string field in database that keeps numbers as string. when I want to order based on this field in Linq as below but orderby does not work well. it orders like this
1 - 2 - 3 - 25 - 11 - 30 - 50 ===> 1 - 11 - 2 - 25 - 3 - 30 - 50
IQueryable<Tbl_Melk> Melks =
from melk in Tbl_Melk
where melk.Mantaghe == Mantaghe && melk.Hoze == Hoze && melk.Block == Block
orderby melk.Melk
select melk;
What says Maurice is right, You may try this:
var Melks = from melk in Tbl_Melk.ToList()
let integer = int.Parse(melk)
orderby integer
where melk.Mantaghe == Mantaghe && melk.Hoze == Hoze && melk.Block == Block
orderby melk.Melk
select melk;
But with that you are losing performance and the IQuerable interface.
Actually, that is the correct order because it's sorting the values in alphabetic order. LINQ cannot tell that the data contains numbers unless you coerce it into a numeric type. Check out this question for one way to sort the way you want.
Linq - Order by number then letters
LeftPad the string with zeros.
Out of my brain and to the lack of EntityFramework not supporting LeftPad:
....
orderby SqlFunctions.Replicate("0", 10 - melk.Melk.Length) + melk.Melk
I have a linq statement that returns a list of records based on where clause
This where clause checks for two parameter values.
Out of which one parameter is optional.
so i need a suggestions if i can switch my where clause based on the optional Parameter
something like this
if(locid==0)
{
where (p.CustomerID == custid)
}
else{
where (p.CustomerID == custid) & (p.LocationID == locid )
}
can any one help me how can i get this work.
thanks
You could try writing it like this:
where (p.CustomerID == custid) && (locid == 0 || p.LocationID == locid )
Yes - queries can be composed (although you don't need this for this particular case as #rsbarro pointed out):
var query = p;
if(locid==0)
query = query.Where( p =>p.CustomerID == custid);
else
query = query.Where( p =>p.CustomerID == custid & p.LocationID == locid);
//any other conditions
As BrokenGlass mentioned, you should use composition:
IQueryable<Foo> query = unfiltered.Where(p => p.CustomerID == custId);
if (locid != 0)
{
query = query.Where(p => p.LocationID == locid);
}
Note that the query is not executed until you start reading data from it, so you needn't worry about this making multiple requests.
It looks like in your original post you were trying to use query syntax piecemeal - that won't work, but the "dot notation" is pretty simple here. You can always create your initial query using a query expression if you want - again, that query won't be executed immediately anyway.