#include <signal.h>
#include <time.h>
#include "Date8b.h"
#include <iomanip>
using namespace std;
bool Date::printyear = true;
Date* Date::td = 0;
Date& Date::today() {
if (!td) {
time_t clk = time(0);
struct tm t = *localtime(&clk);
td = new Date(t.tm_mday, t.tm_mon+1, t.tm_year+1900);
}
return *td;
}
Date::Date(int day, int month, int year)
: d(day), m(month), y(year) {
j = jday(d, m, y);
delete td;
td = 0;
}
Date Date::previous(int desiredDayOfWeek) const {
int delta = weekday() - desiredDayOfWeek;
if (delta <= 0) delta += 7;
return Date(*this) -= delta;
}
const Date& Date::operator+=(long days) {
j += days;
dmy();
return *this;
}
const Date Date::operator+(long days) {
return Date(*this) += days;
}
const Date& Date::operator-=(long days) {
j -= days;
dmy();
return *this;
}
const Date Date::operator-(long days) {
return Date(*this) -= days;
}
ostream& operator<<(ostream& ostr, const Date& d) {
if (Date::printyear)
return ostr << setw(2) << d.day() << '.' << d.monthname() << '.' << d.year();
else
return ostr << setw(2) << d.day() << '.' << d.monthname();
}
bool leapYear(int year) {
return (year&3) == 0 && (year%100 != 0 || year % 400 == 0);
}
bool Date::dayWithinMonth(int day, int month, int year) const {
if (day <= 0 || month<1 || month>12 ) return 0;
int dh = daysInMonth[month-1];
if (leapYear(year) && month == 2) dh++;
return day <= dh;
}
unsigned long Date::jday(int day, int month, int year) const {
if( !dayWithinMonth(day, month, year) ) return 0UL;
if (month > 2) {
month -= 3;
} else {
month += 9;
year--;
}
unsigned long c = year / 100;
unsigned long ya = year - 100*c;
unsigned long jd = ((146097*c)>>2) + ((1461*ya)>>2)
+ (153*month + 2)/5 + day + 1721119;
return jd;
}
void Date::dmy() {
unsigned long jh = j - 1721119;
y = ((jh<<2) - 1) / 146097;
jh = (jh<<2) - 1 - 146097*y;
unsigned long dh = (jh>>2);
jh = ((dh<<2) + 3) / 1461;
dh = (dh<<2) + 3 - 1461*jh;
dh = (dh + 4)>>2;
m = (5*dh - 3)/153;
dh = 5*dh - 3 - 153*m;
d = (dh + 5)/5;
y = 100*y + jh;
if (m < 10)
m += 3;
else {
m -= 9;
y++;
}
}
Date easter(int year) {
long a, b, c, d, e, f, g, h, i, j, k, m, n;
a = year % 19;
j = year % 4;
m = 0;
if (year > 1582) {
b = year / 25 >> 2;
c = year % 100;
d = b >> 2;
e = b % 4;
f = (b + 8) / 25;
g = (b - f + 1) / 3;
h = (19 * a + b - d - g + 15) % 30;
i = c >> 2;
k = (32 + 2 * e + 2 * i - h - j) % 7;
m = (a + 11 * h + 22 * k) / 451;
} else {
b = year % 7;
h = (19 * a + 15) % 30;
k = (2 * j + 4 * b - h + 34) % 7;
}
n = h + k - 7 * m + 21;
return Date(n % 31 + 1, 3 + n / 31, year);
}