Which days are work days in a given date range
Is there a built in function that will tell me which days are work days? this is what i mean,
If I were to choose today's date (6/14/2011), it will give me any inspection numbers clocked out today. This lead time includes weekends. So if I had a customer start a 开发者_如何学编程project on the 10th (Friday) and finish it today; it would show it took about five days, instead of three.
I believe there used to be a function to do this a long long time ago, but I believe that function has since been removed. I believe that you should be able to use something like the following which calculates the business days between two dates:
DateDiff ("d", {Orders.OrderDate}, {Orders.ShipDate}) -
DateDiff ("ww", {Orders.OrderDate}, {Orders.ShipDate}, crSaturday) -
DateDiff ("ww", {Orders.OrderDate}, {Orders.ShipDate}, crSunday)
This gets the total days difference and subtracts the saturdays and sundays from the total. Note this does not include holidays. For that you'd need to maintain them in your own User Function Library and include them in the calculation.
Hope this helps.
This is the solution i came up with. Pretty much if it is anything over 7 days i know how many days to subtract. if it is under 7 days i can still figure out if it spanned the weekend. Crystal reports has a function DayOfWeek that returns a number for the day i.e. Sunday = 1, Monday = 2, etc. If the finish time day number is less than the start time number we know it passed the weekend. and we can subtract 2.
timeDiff is startdate - finishdate.
if({@timeDiff} >= 35) then
{@timeDiff} - 10
else if({@timeDiff} >= 28) then
{@timeDiff} - 8
else if({@timeDiff} >= 21) then
{@timeDiff} - 6
else if({@timeDiff} >= 14) then
{@timeDiff} - 4
else if({@timeDiff} >= 7) then
{@timeDiff} - 2
else if(DayOfWeek({Command.Finishdate}) < DayOfWeek({Command.Startdate})) then
{@timeDiff} - 2
else
{@timeDiff}
I have a more in depth explanation on my website. the link is here
Here is a monster solution that also takes public holidays into account:
// WorkingDays
// Count the number of working days between a start and an end date.
//
// startDate - first date in the interval
// endDate - last date in the interval
// countStartAndEnd - if true 1 feb to 2 feb will count as 2 days
// if false 1 feb to 2 feb will count as 1 day
// given both of them are working days
Function (dateVar startDate, dateVar endDate, optional booleanVar countStartAndEnd := False)
local NumberVar Weeks;
local NumberVar Days;
local NumberVar Hol;
// 5 days for every week (whole or partial)
Weeks := (Truncate (endDate - dayofWeek(endDate) + 1 - (startDate - dayofWeek (startDate) + 1)) /7 ) * 5;
// Number of days in partial weeks (can be positive or negative)
Days := DayOfWeek(endDate) - DayOfWeek(startDate) + 1 +
(if DayOfWeek(startDate) = crSunday then -1 else 0) +
(if DayOfWeek(endDate) = crSaturday then -1 else 0);
// Count number of public holidays in the period
local NumberVar iYear;
local NumberVar i;
for iYear := Year(startDate) to Year(endDate) do (
Local DateVar Array Holidays := getHolidays(iYear);
for i := 1 to uBound(Holidays) do (
local NumberVar hMonth := Month(Holidays[i]);
local NumberVar hDay := Day(Holidays[i]);
local DateVar hDate := cDate(iYear, hMonth, hDay);
if DayOfWeek(hDate) in crMonday to crFriday and
hDate in startDate to endDate then Hol := Hol+1;
);
);
// Return number of working days
Weeks + Days - Hol - toNumber(not countStartAndEnd);
Code above modified from solution found at KenHamady.
The following function is called by the previous function and returns all public holidays:
// getHolidays
// Returns an array with all public holidays for a given year
// These are Swedish holidays. Modify as needed.
Function (Numbervar yyyy)
Datevar Array holidays;
local Datevar holiday;
local Datevar easterSunday := getEasterSunday(yyyy);
// New Years Day
// 1 jan
holiday:=Date(yyyy, 1, 1);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Epiphany
// 6 jan
holiday:=Date(yyyy, 1, 6);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Good Friday
// 2 days before easter sunday
holiday:=cDate(DateAdd("d", -2, easterSunday));
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Holy Saturday
// 1 day before easter sunday
holiday:=cDate(DateAdd("d", -1, easterSunday));
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Easter Sunday
// The first Sunday following the first ecclesiastical full moon that occurs on or after the day of the vernal equinox
holiday:=cDate(DateAdd("d", -2, easterSunday));
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Easter Monday
// 1 day after easter sunday
holiday:=cDate(DateAdd("d", 1, easterSunday));
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Labour day
// 1 may
holiday:=Date(yyyy, 5, 1);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Ascension
// 39 days after easter sunday
holiday:=cDate(DateAdd("d", 39, easterSunday));
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// National day
// 6 june
holiday:=Date(yyyy, 6, 6);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Midsummer's eve
// The friday in the interval 19 june - 25 june
holiday:=cDate(DateAdd("d", 1-dayOfWeek(Date(yyyy, 6, 25), crFriday), Date(yyyy, 6, 25)));
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// All saints' day
// The saturday in the interval 31 october - 6 november
holiday:=cDate(DateAdd("d", 1-dayOfWeek(Date(yyyy, 11, 6), crSaturday), Date(yyyy, 11, 6)));
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Christmas eve
// 24 december
holiday:=Date(yyyy, 12, 24);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// Chritmas day
// 25 december
holiday:=Date(yyyy, 12, 25);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// St. Stephen's Day
// 26 december
holiday:=Date(yyyy, 12, 26);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
// New year's eve
// 31 december
holiday:=Date(yyyy, 12, 31);
Redim Preserve holidays[Ubound(holidays)+1];
holidays[Ubound(holidays)]:=holiday;
holidays;
Code above based on the custom function in this post by craig.
The holiday function need to be able to get the date for easter sunday for a given year:
// getEasterSunday
// Returnes a dateVar of the easter sunday for a given year
//
// Based upon formula from http://aa.usno.navy.mil/faq/docs/easter.php
Function (numberVar yyyy)
local numberVar c := int(yyyy / 100);
local numberVar n := yyyy - 19 * int(yyyy / 19);
local numberVar k := int((c-17)/25);
local numberVar i := c - int(c/4) - int((c-k)/3) + 19*n + 15;
i := i - 30 * int(i/30);
i := i - int(i/28) * ( 1 - int(i/28) * int(29/(i+1)) * int((21-n)/11));
local numberVar j := yyyy + int(yyyy/4) + i + 2 - c + int(c/4);
j := j - 7 * int(j/7);
local numberVar l := i - j;
local numberVar m := 3 + int((l+40)/44);
local numberVar d := l + 28 - 31 * int(m/4);
cDate(yyyy, m , d);
Easter sunday calculation formula from United States Naval Observatory.
精彩评论