void Date::getDMY(unsigned int &d, unsigned int &m, unsigned int &y) { y = baseYear_-1; long tmp = daysSinceBaseDate_; while((tmp -= yearDays(++y)) >= 0); tmp += yearDays(y); m = 0; while ((tmp -= monthDays(++m, y)) >= 0); d = tmp+monthDays(m, y)+1; }
int Date::dmy2dsbd(unsigned int d, unsigned int m, unsigned int y) { if (d < 1 || d > monthDays(m, y) || m < 1 || m > 12 || (y < baseYear_)) { return 0; } int daysSinceBaseDate = 0; unsigned int n; for (n = baseYear_; n < y; ++n) { daysSinceBaseDate += yearDays(n); } for (n = 1; n < m; ++n) { daysSinceBaseDate += monthDays(n, y); } daysSinceBaseDate += d-1; return daysSinceBaseDate; }
/*----------------------------------------------------------------------------- * Obtenção de uma lista com as datas de mudança de hora */ int _getDstDate(const struct tm * t, struct tm * tx) { _DstRules * rules, * pr; char * isdst = tin_getDst(); int i; if (isdst == NULL) return -1; /* * Tradução das regras de formato texto para formato interno */ if (isdst[0] != '\0') { if ((rules = _getDst(isdst)) == NULL) return 0; } else return 0; /* * Interpretação das regras */ for (i = 0, pr = rules; pr->wday != 7 && tx != NULL; ++pr, ++tx, ++i) { /* * O ano em causa */ int year = pr->year == 0 ? t->tm_year : pr->year; /* * Dias desde o inicio do ano */ int yday = yearDays(year, pr->mon, pr->day); /* * Testa se a regra de mudanca de hora e' fixa ou adaptativa */ if (pr->adap) { if ( ! pr->prev) { /* Definição a partir do inicio do mês */ int wday = weekDay(t->tm_year, pr->mon, 1); yday = yearDays(year, pr->mon, 1); yday += pr->wday >= wday ? pr->wday - wday : pr->wday + 7 - wday; yday += (pr->day - 1) * 7; } else { /* Definição a partir do fim do mês */ int wday = weekDay(t->tm_year, pr->mon + 1, 1); yday = yearDays(year, pr->mon + 1, 1); yday -= wday > pr->wday ? wday - pr->wday : wday + 7 - pr->wday; yday -= (pr->day - 1) * 7; } } tx->tm_year = year; tx->tm_mon = pr->mon; tx->tm_mday = _dayMonth(year, yday); // dia no mês tx->tm_wday = (days1970(year, 0, 1) + yday + WDAY) % 7; // dia da semana tx->tm_yday = yday; tx->tm_hour = pr->hour; tx->tm_min = 0; tx->tm_sec = 0; } return i; }
int _isdst(const struct tm * t) { _DstRules * pr; static _DstRules * rules = NULL; static const char * olddst = NULL; char * isdst = tin_getDst(); if (isdst == NULL) return -1; // if (olddst != isdst) { if (isdst[0] != '\0') { if ((rules = _getDst(isdst)) == NULL) return -1; } else return -1; olddst = isdst; // } { int dst = 0; const int hour = t->tm_yday * 24 + t->tm_hour; for (pr = rules; pr->wday != 7; ++pr) if (pr->year <= t->tm_year) { /* * Dias desde o inicio do ano */ int yday = yearDays(t->tm_year, pr->mon, pr->day); /* * Testa se a regra de mudanca de hora e' fixa ou adaptativa */ if (pr->adap) { if ( ! pr->prev) { /* Definição a partir do inicio do mês */ int wday = weekDay(t->tm_year, pr->mon, 1); yday = yearDays(t->tm_year, pr->mon, 1); yday += pr->wday >= wday ? pr->wday - wday : pr->wday + 7 - wday; yday += (pr->day - 1) * 7; } else { /* Definição a partir do fim do mês */ int wday = weekDay(t->tm_year, pr->mon + 1, 1); yday = yearDays(t->tm_year, pr->mon + 1, 1); yday -= wday > pr->wday ? wday - pr->wday : wday + 7 - pr->wday; yday -= (pr->day - 1) * 7; } } /* * Se a hora presente for menor que a proxima mudanca de hora * acabar a pesquisa */ if (hour < yday * 24 + pr->hour) return dst; /* * O inicio do ano comeca sempre em hora solar * Enquanto se mantiver no mesmo ano vai invertendo */ dst = pr->year == (pr + 1)->year ? ! dst : 0; } return dst; } }