matrix report for leaves - c#

I have no.of days, start date and end date stored in table to store no.of leaves of employees.
I want to create report in which user select start date and end date from calendar and report shows the data depending on date selected. But my problem is if the user select a date which is in between start date and end date, I want accurate no.of days for that particular employee.
for ex. the following data saved in database
no of days 3
start date 02/06/2016
end date 04/06/2016
user selected start date 03/06/2016 and end date 04/06/2016 from calendar.
The expected result is: no. of days 2
Please suggest a sql query or C# code
table structure
leaveId empid leavetypeId noofdays startdate enddate
1 76 1 3 2016-06-02 2016-06-04
query i fired like as follows
select noofdays
from table
where startdate='2016-06-03' and enddate='2016-06-04'
and expected result
noofdays = 2

Try following solution:
DECLARE
#pStartDate DATE = {d '2016-06-01'}, -- p = parameter
#pEndDate DATE = {d '2016-06-12'}
SELECT SUM(DATEDIFF(DAY, x.CommonRangeStartDate, x.CommonRangeEndDate) + 1) AS NumOfCommonDays
FROM (VALUES
(1, {d '2016-06-02'}, {d '2016-06-04'}),
(2, {d '2016-06-02'}, {d '2016-06-02'}),
(3, {d '2016-06-04'}, {d '2016-06-10'}),
(4, {d '2016-06-12'}, {d '2016-06-15'}),
(5, {d '2016-06-14'}, {d '2016-06-17'}),
(6, {d '2016-05-01'}, {d '2016-06-18'})
) s(LeaveID, StartDate, EndDate) -- I assume SD & ED's data type is DATE
CROSS APPLY (
SELECT
CASE WHEN s.StartDate >= #pStartDate THEN s.StartDate ELSE #pStartDate END AS CommonRangeStartDate, -- MAX
CASE WHEN s.EndDate <= #pEndDate THEN s.EndDate ELSE #pEndDate END AS CommonRangeEndDate -- MIN
) x
WHERE s.StartDate <= #pEndDate
AND #pStartDate <= s.EndDate
Note #1: Assumptions: StartDate <= EndDate, #pStartDate <= #EndDate
Note #2: If you want to see details then use SELECT * instead of SELECT SUM

Related

SQL Server query to get values between fromdate and todate as well as fromdata, todate

SQL Server query to get values between (from date) to (to date) with from date and to date.
I had tried
select *
from abc
where 1 = 1
and entrydate between '"txt1.Text"' and '"txt2.Text"'
I get result between startdate and enddate but in need values of start date and enddate also
If I had a #StartDate parameter and #EndDate parameter both as Datetimes, I would cast them to dates so you can get:
Select *
From ABC
Where entrydate >= CAST(#StartDate as Date)
and entrydate < DATEADD(d, 1, CAST(#EndDate as Date))
Since the end date would be essentially midnight on the morning of the end date, to include it you have to advance it to the next day, then you can do a less than and the previous day is fully included.

DbFunctions DiffDays Gives wrong answer

I want to get a list from DataBase, where MyDate is today or tomarrow.
I wrote the following code.
_Log("Now: " + DateTime.Now.ToString());
var v = db_TS.TS_Test.Where(x => DbFunctions.DiffDays(x.MyDate,DateTime.Now) < 2);
foreach (var item in v.ToList())
{
_Log("MyDate: " + item.MyDate.ToString());
}
The following is logged:
Now: 11/08/2016 10:50:00
MyDate: 27/09/2017 09:35:00
Please help me to find what went wrong in the code?
Thank you
You should be doing DbFunctions.DiffDays(DateTime.Now,x.MyDate) since it's supposed to work like subtracting the first parameter from the second one, so in your case, the DiffDays is returning a negative number.
Summarizing it if you have DbFunctions.DiffDays(date1,date2)
and date1 > date2 the result will be < 0
and date1 < date2 the result will be > 0
Simplest approach is to check year, month, and day with the current date. Month and year should be the same. Day has to be the same for today and one day less for tomorrow:
var v = db_TS.TS_Test.Where(x => x.MyDate.Year == DateTime.Now.Year &&
x.MyDate.Month == DateTime.Now.Month &&
x.MyDate.Day >= DateTime.Now.Day - 1);
Edit
As pointed out this simplistic scenario won't work for edge cases.
Better option is to subtract a date from today and check what's the result in days. If it's tomorrow then the difference is 1 day or 0 if it's today.
var v = db_TS.TS_Test.Where(x => DateTime.Now.Subtract(x.MyDate).Days <= 1);
please check here from more info of datediff function.
Syntax
-- DATEDIFF ( datepart , startdate , enddate )
-- Example usage
SELECT DATEDIFF(DAY, GETDATE(), GETDATE() + 1) AS DayDiff
SELECT DATEDIFF(MINUTE, GETDATE(), GETDATE() + 1) AS MinuteDiff
SELECT DATEDIFF(SECOND, GETDATE(), GETDATE() + 1) AS SecondDiff
SELECT DATEDIFF(WEEK, GETDATE(), GETDATE() + 1) AS WeekDiff
SELECT DATEDIFF(HOUR, GETDATE(), GETDATE() + 1) AS HourDiff
You can play with here

Select the first and the last day of a month in sql server for a month already stored in SQL Database

I have a small idea for that but i don't know how to interpret it in sql server (MSDN).
if (Month < ActualMonth)
{
(StartDateReq = FirstDayMonth);
(EndDatereq) = LastDayMonth);
}
else if (Month = currenTimeStamp)
{
(EndDateReq = currentTimeStamp);
}
If you have a date in SQL Server, you can get the first and last day of the month using:
select dateadd(day, 1 - day(datecol), datecol) as firstday,
dateadd(day, -1, dateadd(month, 1, dateadd(day, 1 - day(datecol), datecol))) as lasstday
In SQL Server 2012+, you can use the function EOMONTH() for the last day of the month.
Drawing on Gordon's answer:
DECLARE #myDate Date = '2015-10-25'
select DATEADD(DAY, 1 - DAY(#myDate), #myDate) as firstday,
CASE WHEN YEAR(#myDate) = YEAR(GETDATE()) AND
MONTH(#MyDate) = MONTH(GETDATE())
THEN #MyDate
ELSE DATEADD(DAY, -1, DATEADD(MONTH, 1, DATEADD(DAY, 1 - DAY(#myDate), #myDate)))
END as lasstday

Query to display +- 2 days of data but return only selected date itself

I would like to send a MySQL query where I choose a date from my C# programming comboBox e.g. 04/06/2014. Then result should show +-2days including 04/06/2014 itself. i.e. result will ended up showing data from 02/06/2014 till 06/06/2014 (a total of 5 days) in my dataGridView. My MySQL command below shows only the data for 04/06/2014, can someone kindly correct my code? Any help would be much appreciated!
Note: Assuming the 04/06/2014 will be replaced by my C# code comboBox_stockDates.SelectedItem.ToString()
SELECT Prices_Date, Prices_Time, Prices_Open
FROM tableprices
WHERE Ticker_ID = 732
AND DATE_ADD(STR_TO_DATE('04/06/2014', '%d/%m/%Y'), INTERVAL - 2 DAY)
AND DATE_ADD(STR_TO_DATE('04/06/2014', '%d/%m/%Y'), INTERVAL - 1 DAY)
AND Prices_Date = STR_TO_DATE('04/06/2014', '%d/%m/%Y')
AND DATE_ADD(STR_TO_DATE('04/06/2014', '%d/%m/%Y'), INTERVAL + 1 DAY)
AND DATE_ADD(STR_TO_DATE('04/06/2014', '%d/%m/%Y'), INTERVAL + 2 DAY)
ORDER BY Prices_Date ASC, Prices_Time ASC;
Your SELECT filters only the column Price_Date and current date. This one should work for you:
SELECT Prices_Date,
Prices_Time,
Prices_Open
FROM tableprices
WHERE Ticker_ID = 732
AND Prices_Date >= DATE_ADD (STR_TO_DATE ('04/06/2014', '%d/%m/%Y'), INTERVAL -2 DAY)
AND Prices_Date <= DATE_ADD (STR_TO_DATE ('04/06/2014', '%d/%m/%Y'), INTERVAL +2 DAY)
ORDER BY Prices_Date ASC, Prices_Time ASC;
For using the indexes of your table effectively (if there are any) it's better to convert the dates before the query as Chris suggested.
Any reason you can't do the conversion in C#? Seems cleaner.
Then it'd be a select from table where date greater than or equal and date less than or equal.
C# Code:
var dt = DateTime.ParseExact(comboBox_stockDates.SelectedItem.ToString(), "dd/MM/yyyy", System.Globalization.CultureInfo.InvariantCulture);
var start = dt.AddDays(-2);
var end = dt.AddDays(2);
Then select:
SELECT prices_date,
prices_time,
prices_open
FROM tableprices
WHERE ticker_id = 732
AND ( prices_date >= [startdate]
AND prices_date <= [enddate] )
ORDER BY prices_date ASC,
prices_time ASC;
Will this not work for you?

sql query problem

i want to compare two date and time with each other and
i want to select records that "StartTime" is greater than now time and the "StartDate" is greater than now date.
but output is not correct.thanks in advance.
my tabale'records are:
StartDate StartTime
-------------------------------
1389/07/11 11:04
1389/06/23 21:17
1389/06/23 21:32
1389/06/23 22:10
1389/06/26 12:34
1389/06/27 17:29
1389/06/27 18:13
1389/06/27 20:27
1389/06/28 09:41
1389/07/18 10:46
1389/07/05 22:00
1389/07/15 24:00
output is:
when the query is : (1)
SELECT StartDate, StartTime
FROM Proj
WHERE (StartDate < '1389/07/15 ') AND (StartTime <= '20:20 ')
StartDate StartTime
-------------------------------
1389/07/11 11:04
1389/06/26 12:34
1389/06/28 09:41
1389/07/18 10:46
output is:
when the query is: (2)
SELECT StartDate, StartTime
FROM Proj
WHERE (StartDate > '1389/07/15 ') AND (StartTime >= '20:20 ')
StartDate StartTime
-------------------------------
NULL NULL
the correct output should be:
StartDate StartTime
-------------------------------
1389/07/18 10:46
i use persian date.
Just taking what you have above and the description of your problem, the query should be:
select * from test where date>'2010/10/05' and time>='20:22'
If you post more details about your problem and the schema in which you're working we'll be able to help you more.
I want to select records that "time" is greater than now time and the "date" is greater than now date.
First off to get the current datetime (your now), you can use the SQL function GETDATE().
So if you happen to have a datetime column you could just do
SELECT * FROM Test WHERE LogDateTime >= GETDATE()
This will return every record in the table Test of which the datetime value inside the LogDateTime column is in the future.
Now, although it's a little bit more complicated, the same can be used when you have split the date and the time into separate columns.
SELECT * FROM Test
WHERE CONVERT(datetime, LogDate + ' ' + LogTime) >= GETDATE()
If LogDate or LogTime are nullable columns you could use ISNULL(<columnName>, <defaultvalue>) to be safe.
it solved:
SELECT StartDate, StartTime
FROM Proj
WHERE (StartTime < '20:20 ') AND (StartDate = '1389/07/15') OR
(StartDate > '1389/07/15')

Categories

Resources