⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 date.cpp

📁 国外网站上的一些精典的C程序
💻 CPP
字号:
/* * This file is part of PB-Lib C/C++ Library * * Copyright (c) 1995, 1996 Branislav L. Slantchev * A Product of Silicon Creations, Inc. * * This class is hereby donated to the SNIPPETS collection (maintained * by Bob Stout). You are granted the right to use the code contained * herein free of charge as long as you keep this copyright notice intact. * * Contact: 73023.262@compuserve.com*/#include "date.hpp"const int             zDate::ReformYear      = 1582;const ulong           zDate::ReformDayNumber = 577737L;const zDate::month    zDate::ReformMonth     = zDate::oct;        zDate::week_day zDate::BeginDSTDay     = zDate::sun;        zDate::month    zDate::BeginDSTMonth   = zDate::apr;        zDate::week_day zDate::EndDSTDay       = zDate::sun;        zDate::month    zDate::EndDSTMonth     = zDate::oct;zDate::zDate(){      Set(jan, 1, 1);}zDate::zDate(month aMonth, int aDay, int aYear){      Set(aMonth, aDay, aYear);}zDate::zDate(int dayOfYear, int year){      m_day   = 31;      m_month = dec;      m_year  = year - 1;      m_dayno = MakeDayNumber();      FromDayNumber(m_dayno + dayOfYear);}zDatezDate::Set(month aMonth, int aDay, int aYear){      m_month = aMonth;      m_day   = aDay;      m_year  = aYear;      m_dayno = MakeDayNumber();      return *this;}zDate::zDate(const zDate &aDate){      m_month = aDate.m_month;      m_day   = aDate.m_day;      m_year  = aDate.m_year;      m_dayno = aDate.m_dayno;}zDate::zDate(ulong nJulian){      FromDayNumber(nJulian);}zDate::zDate(const struct tm *tmDate){      m_month = (month)(tmDate->tm_mon + 1);      m_day   = tmDate->tm_mday;      m_year  = tmDate->tm_year + 1900;      m_dayno = MakeDayNumber();}zDatezDate::Today(){      time_t     secs_now = time(0);      struct tm *time_now = localtime(&secs_now);      zDate      today(time_now);      return today;}BooleanzDate::operator!=(const zDate &aDate) const{      return Boolean(m_dayno != aDate.m_dayno);}BooleanzDate::operator==(const zDate &aDate) const{      return Boolean(m_dayno == aDate.m_dayno);}BooleanzDate::operator<(const zDate &aDate) const{      return Boolean(m_dayno < aDate.m_dayno);}BooleanzDate::operator<=(const zDate &aDate) const{      return Boolean(m_dayno <= aDate.m_dayno);}BooleanzDate::operator>(const zDate &aDate) const{      return Boolean(m_dayno > aDate.m_dayno);}BooleanzDate::operator>=(const zDate &aDate) const{      return Boolean(m_dayno >= aDate.m_dayno);}zDate&zDate::operator=(const zDate &aDate){      m_day   = aDate.m_day;      m_month = aDate.m_month;      m_year  = aDate.m_year;      m_dayno = aDate.m_dayno;      return *this;}intzDate::DaysInMonth(month aMonth, int aYear){      static const int days[13] = {0,31,28,31,30,31,30,31,31,30,31,30,31};      if( aYear == ReformYear && aMonth == ReformMonth ) return 21;      return days[aMonth] + (feb == aMonth && IsLeapYear(aYear));}intzDate::DayOfYear() const{      zDate first(jan, 1, m_year);      return 1 + (int)(m_dayno - first.m_dayno);}intzDate::DaysInYear(int year){      int days = 365 + IsLeapYear(year);      // 10 days cancelled by the reform of pope Gregor XIII      if( year == ReformYear ) return days - 10;      else return days;}BooleanzDate::IsLeapYear(int year){      if( year % 4 ) return False;  // if not divisible by 4, not leap      if( year < ReformYear ) return True; // before this year, all were leap      if( year % 100 ) return True; // by 4, but not by 100 is leap      if( year % 400 ) return False;      // not by 100 and not by 400 not leap      return True;}BooleanzDate::IsValid(month aMonth, int aDay, int aYear){      return Boolean(               aYear  > 0            && aMonth >= jan && aMonth <= dec            && aDay   >  0   && aDay   <= DaysInMonth(aMonth, aYear)      );}intzDate::Age(const zDate &birthday) const{      int age = m_year - birthday.m_year - 1;      if( m_month > birthday.m_month ) age++;      else if( m_month == birthday.m_month && m_day >= birthday.m_day ) age++;      return age;}zDatezDate::operator+(int nDays) const{      return zDate(m_dayno + (long)nDays);}zDatezDate::operator+(long nDays) const{      return zDate(m_dayno + nDays);}zDatezDate::operator-(int nDays) const{      return zDate(m_dayno - (long)nDays);}zDatezDate::operator-(long nDays) const{      return zDate(m_dayno - nDays);}longzDate::operator-(const zDate &aDate) const{      return (long)(m_dayno - aDate.m_dayno);}zDate&zDate::operator+=(int nDays){      FromDayNumber(m_dayno + (long)nDays);      return *this;}zDate&zDate::operator+=(long nDays){      FromDayNumber(m_dayno + nDays);      return *this;}zDatezDate::operator++(){      FromDayNumber(m_dayno + 1L);      return *this;}zDatezDate::operator++(int){      zDate date(*this);      FromDayNumber(m_dayno + 1L);      return date;}zDatezDate::operator--(){      FromDayNumber(m_dayno - 1L);      return *this;}/* postfix */zDatezDate::operator--(int){      zDate date(*this);      FromDayNumber(m_dayno - 1L);      return date;}zDate&zDate::operator-=(int nDays){      FromDayNumber(m_dayno - (long)nDays);      return *this;}zDate&zDate::operator-=(long nDays){      FromDayNumber(m_dayno - nDays);      return *this;}intzDate::WeekOfYear() const{      zDate first(jan, 1, m_year);      return 1 + int((m_dayno - first.m_dayno + 1) / 7);}intzDate::WeekOfMonth() const{      int abs_mday = m_day + zDate(m_month, 1, m_year).DayOfWeek() - 1;      return 1 + ((abs_mday - DayOfWeek()) / 7);}intzDate::WeeksInYear(int year){      return zDate(dec, 31, year).WeekOfYear();}zDatezDate::AddWeeks(int nWeeks) const{      zDate date(*this);      date += (long)nWeeks * 7L;      return date;}zDatezDate::AddYears(int nYears) const{      zDate date(*this);      int   delta = nYears > 0 ? -1 : 1;      int   year = m_year;      long  days = 0;      while( nYears ){            nYears += delta;            year   -= delta;            days   += DaysInYear(year);      }      date += (-delta * days);      return date;}zDate::operator long() const{      return DayNumber();}/* * arguably useful routine, you can access the date object as an array, * with [0] == day (1..31), [1] == month (1..12), [2] == year - 1900*/charzDate::operator[](int index) const{      switch( index ){            case 0 : return m_day;            case 1 : return m_month;            case 2 : return m_year - 1900;            default: return -1;      }}intzDate::DaysInMonth() const{      return DaysInMonth(m_month, m_year);}intzDate::DaysInYear() const{      return DaysInYear(m_year);}intzDate::WeeksInYear() const{      return WeeksInYear(m_year);}BooleanzDate::IsValid() const{      return IsValid(m_month, m_day, m_year);}BooleanzDate::IsLeapYear() const{      return IsLeapYear(m_year);}ulongzDate::MakeDayNumber() const{      long days;      long year  = (long)m_year - 1L;      // get all days plus all leap years, minus non-leap years      days = year * 365L + year / 4L - year / 100L + year / 400L;      // the years before 1582 were all leap if divisible by 4      if( year > ReformYear ) days += 12;      else{            days += year / 100L;            days -= year / 400L;      }      // get the days for the month up to the current one      for( int i = jan; i < m_month; ++i )            days += DaysInMonth((month)i, m_year);      // now add the current days of the month      days += m_day;      // now adjust for the 10 missing days (Oct 4 - Oct 15, 1582)      if( days > ReformDayNumber ) days -= 10L;      // we have the current day number now      return days;}zDate::week_dayzDate::DayOfWeek() const{      const week_day wdays[7] = {sun,mon,tue,wed,thu,fri,sat};      return wdays[(int)(((m_dayno % 7) + 5) % 7)];}voidzDate::FromDayNumber(ulong dayno){      m_dayno = dayno;      if( dayno > ReformDayNumber ) dayno += 10L;      m_year = (int)(dayno / 365);      m_day = (int)(dayno % 365L);      if( m_year < 1700 ) m_day -= (m_year / 4);      else{            m_day -= (m_year / 4);            m_day += (m_year / 100);            m_day -= (m_year / 400);            m_day -= 12;      }      while( m_day <= 0 ){            m_day += (365 + IsLeapYear(m_year));            m_year--;      }      // m_year is the number of elapsed years, add 1 to get current      m_year += 1;      // figure out the month and current day too      for( m_month = jan; m_month <= dec; m_month = (month)(m_month + 1) ){            int days = DaysInMonth(m_month, m_year);            if( m_day <= days ) break;            else m_day -= days;      }}BooleanzDate::IsDST() const{      return IsDST(*this);}/* * DST (Daylight Savings Time) starts at 2:00a on the first Sunday of * April and ends at 2:00a on the last Sunday of October (US rules)*/zDatezDate::BeginDST(int year){      zDate date(BeginDSTMonth, 1, year);      while( BeginDSTDay != date.DayOfWeek() ) date++;      return date;}zDatezDate::EndDST(int year){      zDate date(EndDSTMonth, 31, year);      while( EndDSTDay != date.DayOfWeek() ) date--;      return date;}zDatezDate::BeginDST() const{      return BeginDST(m_year);}zDatezDate::EndDST() const{      return EndDST(m_year);}BooleanzDate::IsDST(const zDate &date){      return Boolean( date >= date.BeginDST() && date <= date.EndDST() );}zDate::moon_phasezDate::MoonPhase() const{      return MoonPhase(*this);}zDate::moon_phasezDate::MoonPhase(const zDate &date){      ulong phase = date.m_dayno;      phase *= 9693L;      phase /= 35780L;      phase -= 4L;      phase %= 8L;      return (moon_phase)phase;}zDatezDate::Easter() const{      return Easter(m_year);}/* * i won't pretend i know exactly how this algorithm works. * i used the one specified by the US Naval Observatory*/zDatezDate::Easter(int year){      int c, n, k, i, j, l, m, d;      c = year / 100;      n = year - 19 * (year / 19);      k = (c - 17) / 25;      i = c - c / 4 - (c - k) / 3 + 19 * n + 15;      i = i - 30 * (i / 30);      i = i - (i / 28) * (1 - (i / 28) * (29 / (i + 1)) * ((21 - n) / 11));      j = year + year / 4 + i + 2 - c + c / 4;      j = j - 7 * (j / 7);      l = i - j;      m = 3 + (l + 40) / 44;      d = l + 28 - 31 * (m / 4);      return zDate((month)m, d, year);}/* * this is a peculiar function - when months are added (or subtracted), * what really happens is that the month number is modified (with the * appropriate year adjustments too). if the resulting month/day combination * is invalid (i.e. Apr 31), the days will spill into the next month (in * the case with the example, the new date will be May 1). If we are * subtracting months and we end up with an invalid date, the difference * will be subtracted from the days (the month stays the same): this means * that March 31, 1996 (leap year) minus 1 month = Feb 27, 1996*/zDatezDate::AddMonths(int nMonths) const{      int mon  = m_month + nMonths;      int year = m_year;      int day  = m_day;      int mdays;      while( mon < 1 ){            mon += 12;            year--;      }      while( mon > 12 ){            mon -= 12;            year++;      }      mdays = DaysInMonth((month)mon, year);      if( day > mdays ){            if( nMonths < 0 ) day = mdays - (day - mdays);            else{                  day -= mdays;                  mon++;                  if( mon > 12 ){                        year++;                        mon = 1;                  }            }      }      return zDate((month)mon, day, year);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -