How to pass 2 dates in .Where? - c#

currently in the code I am outputting the employees table which have end dates of anything from before today's date and up to 90 days. I am trying to make it so only employees with maximum -30 days and + 90 of today's date.
(Fairly new so be easy)
(NOT SURE HOW TO CORRECTLY USE 2 DATES FOR .ADDDAYS )
Thanks
public ActionResult Index()
{
var employees = db.employees;
var today = DateTime.Today.AddDays(90);
var past = DateTime.Today.AddDays(-30);
var q = db.employees.Where(t => t.EndDate <= today );
return View(q.OrderByDescending(t => t.EndDate));
}

Why can't you use a AND (&&) condition like
var q = db.employees.Where(t => t.EndDate <= today && t.EndDate >= past);

It is simple by using conditional-AND && operator & combining both queries as single line:
var q = db.employees.Where(t => t.EndDate >= past && t.EndDate <= today)
.OrderByDescending(t => t.EndDate);
return View(q);

Try following code. You can add the OrderByDescending(t => t.EndDate) on the first line of code.
var q = db.employees.Where(t => t.EndDate >= past && t.EndDate<= today)OrderByDescending(t => t.EndDate);
return view(q);

Related

How can I group datetime using Linq method syntax but ignoring time section

I'm working on an ASP.NET MVC app written in C#, and I need to display sum of how many times people have viewed videos captured in a SQL database. I'm able to do it in SQL:
SELECT
CAST([Date] AS DATE),
SUM([Views])
FROM
db
WHERE
[DATE] >= '2022-01-28'
AND [DATE] <= '2022-07-28'
GROUP BY
CAST([Date] AS DATE)
But, now the problem is to translate it to Linq in my controller, this is what I have so far (where start and end date are variables):
var data = (Context.Where(w => w.Date >= startDate && w.Date <= endDate)
.GroupBy(g => new { date = g.Date })
.Select(s => new { date = s.Key, sum = s.Sum(c => c.Views) })).ToList();
This will work but will group by date and time which has more rows.
For example, what my code returns:
date = 3/3/2022 3:00:00 AM, sum = 1
date = 3/3/2022 4:00:00 AM, sum = 2
date = 3/3/2022 5:00:00 AM, sum = 3
What I want:
date = 3/3/2022, sum = 6
You can simply use EntityFunctions.TruncateTime. I had in the past tried to put in a PR to allow using DateTime.Date, not sure if it ever landed.
var data = (Context
.Where(w => w.Date >= startDate && w.Date <= endDate)
.GroupBy(g => EntityFunctions.TruncateTime(g.Date))
.Select(s => new { date = s.Key, sum = s.Sum(c => c.Views) })
).ToList()

Linq Min in Select new & Multiple GroupBy columns

I want to write following query in Linq
INSERT INTO INOUTNEW (CODE,INDATE,TIME_DATE1,INOUTFLAG,TIME_FLD1,TIME_FLD2,TIME_FLD3)
SELECT CODE,MIN(INDATE),TIME_DATE1,'I',TIME_FLD1,TIME_FLD2,'31/05/2015' FROM INOUT
WHERE TIME_FLD1='T0003' AND INDATE >= '31/05/2015' AND INDATE <= '31/05/2015'
AND TIME_DATE1='31/05/2015'
GROUP BY CODE,TIME_DATE1,TIME_FLD1,TIME_FLD2
SO I am trying this :-
var data = ctx.tblInOut.Where(m => m.CompanyId == companyId && m.Time_Field1 == item.ShiftCode && m.InDate == StrInStart && m.InDate <= StrInEnd && m.Time_Date1 == InputDate).Select(m =>
new
{
EmployeeId = m.EmployeeId,
InDate = Min(m.InDate),
Time_Date1 = m.Time_Date1,
InOutFlag = m.InOutFlag
}).ToList();
I am stuck in Min Part. How to get Min in Select? And How to add multiple GroupBy in Linq?
Try something like this:
var data = ctx.tblInOut
.Where(m =>
m.CompanyId == companyId &&
m.Time_Field1 == item.ShiftCode &&
m.InDate == StrInStart &&
m.InDate <= StrInEnd &&
m.Time_Date1 == InputDate
)
.GroupBy(m =>
new {
m.Code,
m.Time_Date1,
m.Time_FLD1,
m.Time_FLD2
})
.Select(g =>
new
{
m.Key.Code,
InDate = m.Min(gg => gg.InDate),
m.Key.Time_Date1,
Something = "I",
m.Key.Time_FLD1,
m.Key.Time_FLD2,
SomeDate = "31/05/2015"
}).ToList();
To get Min, you must group first - otherwise it's trying to call Min on a single element.
.Key simply references the key of the group (in this case, a tuple of Code, Date1, Time_FLD1, Time_FLD2)

LINQ Sum of prices in each month in loop?

So I'm trying to have a list of profits in each month from my database.
I want to do this in loop, I thnik it will be the best soulution.
Here we have a loop, that I want to count a profit for each month.
using (var context = new ModelContext("ConnectionStringDbMagazynier"))
{
for (int i = 0; i < 12; i++)
{
decimal q = (from ar in context.Archives
where ar.SalesDate <= DateTime.Now.AddYears(-1).AddMonths(i + 1) && ar.SalesDate >= DateTime.Now.AddYears(-1).AddMonths(i)
let sum = context.Archiwum.Sum(x => x.Price)
select sum);
profits[i] = decimal.ToDouble(q);
}
}
from this query i get an error:
Error 2 Cannot implicitly convert type 'System.Linq.IQueryable<decimal>' to 'decimal'
My question is, how to make it witohut error? and is this solution ok? What in case, that i didn't sell anything in partiuclar month and the sum is null?
It's easier to use lambda syntax in this case.
var q = context.Archives
.Where(ar => ar.SalesDate <= DateTime.Now.AddYears(-1).AddMonths(i + 1) && ar.SalesDate >= DateTime.Now.AddYears(-1).AddMonths(i))
.Sum(x => x.Price);
Or if you really like the query syntax
var records = (from ar in context.Archives
where ar.SalesDate <= DateTime.Now.AddYears(-1).AddMonths(i + 1) && ar.SalesDate >= DateTime.Now.AddYears(-1).AddMonths(i)
select ar);
profits[i] = records.Sum(x => x.Price);
var q = context.Archives
.Where(p => p.SalesDate <= DateTime.Now.AddYears(-1).AddMonths(i + 1) && p.SalesDate >= DateTime.Now.AddYears(-1).AddMonths(i))
.Sum(x => x.Price.HasValue ? x.Price.Value : 0);
It's possible get month stat without loop
var grouped = context.Archives.Where(p=> p.SalesDate <= DateTime.Now.AddYear(-1))
.GroupBy(k => new {Year = k.Year, Month = k.Month})
.Select(p=> {Date = p.Key, Sum = p.Sum(x=> x.Price.HasValue ? x.Price.Value : 0)})

How to write the following query in LINQ

I have a sql query and would like to convert it into linq
SELECT CAST([Date] AS DATE),
COUNT([ID]) AS 'Amount of Systems'
FROM [DemoDB].[dbo].[Servers]
WHERE [ServerID] IN ('ServerX') AND [Type] = 'Complete'
GROUP BY CAST([Date] AS DATE)
ORDER BY CAST([Date] AS DATE)
this will return the result as follows
What I have tried
//fromDP and toDP are the names of the Datepicker's
var query = (this.db.Servers
.Where(x => x.Date >= fromDP.SelectedDate.Value &&
x.Date <= toDP.SelectedDate.Value));
var query_Success = query.Count(p => p.Type == "Complete"
&& (p.ServerID == "ServerX"));
and I have the result as Count on the whole ( for example, if I select from from April 1st to April 15th , the result is the sum of all "complete"), but I need count for each day in this selected range. the result I will bind to the column chart.
how to proceed ?
If I understood correctly the author wants to use only the date without the time. To do this with EF we can use the method EntityFunctions.TruncateTime for trimming the time portion. I will build on #steaks answer:
db.Servers.Where(s => s.ServerId == "ServerX" && s.Type == "Complete")
.GroupBy(s => EntityFunctions.TruncateTime(s.Date))
.OrderBy(s => s.Key)
.Select(g => new {Date = g.Key, AmountOfSystems = g.Count()});
this.db.Servers.Where(s => s.ServerId == "ServerX" && s.Type == "Complete")
.GroupBy(s => s.Date)
.OrderBy(s => s.Key)
.Select(g => new { Date = g.Key, AmountOfSystems = g.Count() });
Change the Where clause to read
Where(s => s.ServerId == "ServerX" && s.Type == "Complete" && s.Date >= fromDP.SelectedDate.Value && s.Date <= toDP.SelectedDate.Value)
to filter to a limited date range.
EDIT
As #vvs0205 suggested. Use EntityFunctions class to manipulate the date column as you please: http://msdn.microsoft.com/en-us/library/system.data.objects.entityfunctions.aspx
Something like this
var fromDate = fromDP.SelectedDate.Value;
var toDate= toDP.SelectedDate.Value;
var q = from server in this.db.Servers
where (server.Date >= fromDate && server.Date<=toDate && server.ServerID="ServerX" && server.Type=="Complete")
group server by server.Date
into g
orderby g.Key
select new
{
Date = g.Key,
Count = g.Count()
};
var results = q.ToList();

how to select a weeks amount of dates from a database?

What I am trying to do is search my database (ado.net with linq to sql) for all entrys within the last week.
The database has a field called date and I need the entries that are 7 days previous to the current date.
var records = (from r in context.PumpInfoTables
where r.Date.Equals(DateTime.Now)
//&& where r.date <= 7 days <--help
select r);
so I am looking for some help with this query, is there a between function that can be used?
DateTime weekFromNow = DateTime.Now.AddDays(-7);
var records = (from r in context.PumpInfoTables
where r.Date < DateTime.Now
&& r.Date >= weekFromNow
select r);
This is really simple:
var oneWeekAgo = DateTime.Today.AddDays(-7);
var records = (from r in context.PumpInfoTables
where r.Date >= oneWeekAgo
select r);
This assumes that you don't have entries from the future. If you do have, use this instead:
var today = DateTime.Today;
var oneWeekAgo = today.AddDays(-7);
var records = (from r in context.PumpInfoTables
where r.Date >= oneWeekAgo && r.Date <= today + 1
select r);
Please note:
My code uses DateTime.Today instead of DateTime.Now, assuming you are only interested in the date part, not the time.
Something like this?:
var records = (from r in context.PumpInfoTables
where r.Date > DateTime.Today.AddDays(-7)
select r);

Categories