Listing 1 介绍日期比较函数
// date4.h
class Date
{
int month;
int day;
int year;
public:
// Constructors
Date()
{month = day = year= 0;}
Date(int m, int d, int y)
{month = m; day = d; year = y;}
// Accessor Functions
int get_month() const
{return month;}
int get_day() const
{return day;}
int get_year() const
{return year;}
Date * interval(const Date&) const;
int compare(const Date&) const;
};
// End of File
Listing 2 间隔和比较成员的实现
// date4.cpp
#include "date4.h"
inline int isleap(int y)
{return y%4 == 0 && y%100 != 0 || y%400 == 0;}
static int dtab[2][13] =
{
{0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
{0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}
};
Date * Date::interval(const Date& d2) const
{
static Date result;
int months, days, years, prev_month;
// Compute the interval - assume d1 precedes d2
years = d2.year - year;
months = d2.month - month;
days = d2.day - day;
// Do obvious corrections (days before months!)
//
// This is a loop in case the previous month is
// February, and days < -28.
prev_month = d2.month - 1;
while (days < 0)
{
// Borrow from the previous month
if (prev_month == 0)
prev_month = 12;
-months;
days += dtab[isleap(d2.year)][prev_month-];
}
if (months < 0)
{
// Borrow from the previous year
-years;
months += 12;
}
// Prepare output
result.month = months;
result.day = days;
result.year = years;
return &result;
}
int Date::compare(const Date& d2) const
{
int months, days, years, order;
years = year - d2.year;
months = month - d2.month;
days = day - d2.day;
// return <0, 0, or >0, like strcmp()
if (years == 0 && months == 0 && days == 0)
return 0;
else if (years == 0 && months == 0)
return days;
else if (years == 0)
return months;
else
return years;
}
// End of File
</pre>
Listing 3 日期比较成员函数的测试
// tdate4.cpp
#include <stdio.h>
#include "date4.h"
void compare_dates(const Date& d1, const Date& d2)
{
int compval = d1.compare(d2);
char *compstr - (compval < 0) ? "precedes" :
((compval > 0) ? "follows" : "equals"};
printf("%d/%d/%d %s %d/%d/%d\n",
d1.get_month(),d1.get_day(0),d1.get_year(),
compstr,
d2.get_month(),d2.get_day(),d2.get_year());
}
main()
{
Date d1(1,1,1970);
compare dates(d1,Date(10,1,1951));
compare_dates{d1,Date(1,1,1970));
compare_dates(d1,Date(12,31,1992));
return 0;
}
/* OUTPUT
1/1/1970 follows 10/1/1951
1/1/1970 equals 1/1/1970
1/1/1970 precedes 12/31/1992
*/
// End of File
Listing 4 为 Date class定义相关的运算符
// date5.h
class Date
{
int month;
int day;
int year;
public:
// Constructors
Date()
{month = day = year = 0;}
Date(int m, int d, int y)
{month = m; day = d; year = y;}
// Accessor Functions
int get_month() const
{return month;}
int get_day() const
{return day;}
int get_year() const
{return year;}
Date * interval(const Date&) const;
int compare(const Date&) const;
// Relational operators
int operator<(const Date& d2) const
{return compare(d2) < 0;}
int operator<=(const Date& d2) const
{return compare(d2) <= 0;}
int operator>(const Date& d2) const
{return compare(d2) > 0;}
int operator>=(const Date& d2) const
{return compare(d2) >= 0;}
int operator!=(const Date& d2) const
{return compare(d2) != 0;}
int operator!=(const Date& d2) const
{return compare(d2) !=0;}
};
// End of File
Listing 5 使用日期类里相关的运算符
// tdate5.cpp
#include <stdio.h>
#include <stdlib.h>
#include "date5.h"
void compare_dates(const Date& d1, const Date& d2)
{
char *compstr = (d1 < d2) ? "precedes" :
((d1 > d2) ? "follows" : "equals");
printf("%d/%d/%d %s %d/%d/%d\n",
d1.get_month(),d1.get_day(),d1.get_year(),
compstr,
d2.get_month(),d2.get_day(),d2.get_year());
}
main()
{
Date d1(1,1,1970);
compare_dates(d1,Date(10,1,1951));
compare_dates(d1,Date(1,1,1970));
compare_dates(d1,Date(12,31,1992));
return 0;
}
/* OUTPUT
1/1/1970 follows 10/1/1951
1/1/1970 equals 1/1/1970
1/1/1970 precedes 12/31/1992
*/
// End of File
Listing 6 为 Date类添加二元和一元的"-"运算符
// date6.h
class Date
{
int month;
int day;
int year;
public:
// Constructors
Date()
{month = day = year = 0;}
Date(int m, int d, int y)
{month = m; day = d; year = y;}
// Accessor Functions
int get_month() const
{return month;}
int get_day() const
{return day;}
int get_year() const
{return year;}
Date operator-(const Date& d2) const;
Date& operator-()
{month = -month; day = -day; year = -year;
return *this;}
int compare(const Date&) const;
// Relational operators
int operator<(const Date& d2) const
{return compare(d2) < 0;}
int operator<=(const Date& d2) const
{return compare(d2) <= 0;}
int operator>(const Date& d2) const
{return compare(d2) > 0;}
int operator>=(const Date& d2) const
{return compare(d2) >= 0;}
int operator==(const Date& d2) const
{return compare(d2) == 0;}
int operator!=(const Date& d2) const
{return compare(d2) != 0;}
};
// End of File
Listing 7 二元"-"运算符的实现
// date6.cpp
#include <assert.h>
#include "date6.h"
inline int isleap(int y)
{return y%4 == 0 && y%100 != 0 || y%400 == 0;}
static int dtab[2][13] =
{
{0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
{0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}
};
Date Date::operator-(const Date& d2) const
{
int months, days, years, prev_month, order;
const Date * first, * last;
// Must know which date is first
if (compare(d2) <= 0)
{
// this <= d2
order = -1;
first = this;
last = &d2;
}
else
{
order = 1;
first = &d2;
last = this;
}
// Compute the interval; first <= last
years = last->year - first->year;
months = last->month - first->month;
days = last->day - first->day;
assert(years >= 0 && months >= 0 && days >= 0);
// Do obvious corrections (days before months!)
// This is a loop in case the previous month is
// February, and days < -28.
prev_month = last->month - 1;
while (days < 0)
{
// Borrow from the previous month
if (prev_month == 0)
prev_month = 12;
--months;
days += dtab[isleap(last->year)][prey_month--];
}
if {months < 0)
{
// Borrow from the previous year
--years;
months += 12;
}
// Return a date object with the interval
if (order == -1)
return Date(-months,-days,-years);
else
return Date(months, days, years);
}
int Date::compare(const Date& d2) const
{
// same as in Listing 2
}
// End of File
Listing 8 两个日期相减
// tdate6.cpp:
#include <stdio.h>
#include "date6.h"
main()
{
Date d1(1,1,1970), d2(12,8,1992);
Date result = d1 - d2;
printf("years: %d, months: %d, days: %d\n",
result.get_year(),
result.get_month(),
result.get_day());
result = d2 - d1;
printf("years: %d, months: %d, days: %d\n",
result.get_year(),
result.get_month(),
result.get_day());
int test = d1 - d2 == -(d2 - d1);
printf("d1 - d2 == -(d2 - d1)? %s\n",
test ? "yes" : "no");
return 0;
}
/* OUTPUT
years: -22, months: -11, days: -7
years: 22, months: 11, days: 7
d1 - d2 == -(d2 - d1)? yes
*/
// End of File
Listing 9 为Date类增加输入输出流
// date7.h
class ostream;
class Date
{
int month;
int day;
int year;
public:
// Constructors
Date()
{month = day = year = 0;}
Date(int m, int d, int y)
{month = m; day = d; year = y;}
// Accessor Functions
int get_month() const
{return month;}
int get_day() const
{return day;}
int get_year() const
{return year;}
Date operator-(const Date& d2) const;
Date& operator-()
{month= -month; day = -day; year = -year;
return *this;}
int compare(const Date&) const;
// Relational operators
int operator<(const Date& d2) const
{return compare(d2) < 0;}
int operator<=(const Date& d2) const
{return compare(d2) <= 0;)
int operator>(const Date& d2) const
{return compare(d2) > 0;}
int operator>=(const Date& d2) const
{return compare(d2) >= 0;}
int operator==(const Date& d2) const
{return compare(d2) == 0;}
int operator!=(const Date& d2) const
{return compare(d2) != 0)
// I/O operators
friend ostream& operator<<(ostream&, const Date&);
friend istream& operator>>(istream&, Date&);
};
// End of File
Listing 10 实现Date类的stream I/O函数
#include <iostream.h>
#include "date7.h"
ostream& operator<<(ostream& os, const Date& d)
{
os << d.month << '/' << d.day << '/' << d.year;
return os;
}
istream& operator>>(istream& is, Date& d)
{
char slash;
is >> d.month >> slash >> d.day >> slash >> d.year;
return is;
}
// End of File
Listing 11 举例说明Date 类对象的stream I/O
// tdate7.cpp:
#include <iostream.h>
#include "date7.h"
main()
{
Date d1, d2;
cout << "Enter a date: ";
cin >> d1;
cout << "Enter another date: ";
cin >> d2;
cout << "d1 - d2 = "<< d1 - d2 << endl;
cout << "d2 - d1 = "<< d2 - d1 << endl;
return 0;
}
/* OUTPUT
Enter a date: 10/1/1951
Enter another date: 5/1/1954
d1 - d2 = -7/0/-2
d2 - d1 = 7/0/2
*/
// End of File
Listing 12 定义静态成员
// date8.h
// Forward declarations
class istream;
class ostream;
class Date
{
int month;
int day;
int year;
static int dtab[2][13];
public:
// Constructors
Date(); // Get today's date (see .cpp file)
Date(int m, int d, int y)
{month = m; day = d; year = y;}
// Accessor Functions
int get_month() const
{return month;}
int get_day() const
{return day;}
int get_year() const
{return year;}
Date operator-(const Date& d2) const;
Date& operator-()
{month = -month; day = -day; year = -year;
return *this;}
int compare(const Date&) const;
// Relational operators
int operator<(const Date& d2) const
{return compare{d2) < 0;}
int operator<=(const Date& d2) const
{return compare(d2) <= 0;}
int operator>(const Date& d2) const
{return compare(d2) > 0;}
int operator>=(const Date& d2) const
{return compare(d2) >= 0;}
int operator==(const Date& d2) const
{return compare(d2) == 0;}
int operator!=(const Date& d2) const
{return compare(d2) != 0;}
// Stream I/O operators
friend ostream& operator<<(ostream&, const Date&);
friend istream& operator>>(istream&, Date&);
static int isleap(int y)
{return y%4 == 0 && y%100 != 0 || y%400 == 0;}
};
// End of File
Listing 13 Date类的最终实现
// date8.cpp
#include <iostream.h>
#include <time.h>
#include <assert.h>
#include "date8.h"
// Must initialize statics outside the class definition
int Date::dtab[2][13] =
{
{0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31},
{0, 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31}
};
Date Date::operator-(const Date& d2) const
{
int months, days, years, prev_month, order;
const Date * first, * last;
// Must know which date is first
if (compare(d2) <= 0)
{
// this <= d2
order= -1;
first = this;
last = &d2;
}
else
{
order = 1;
first = &d2;
last = this;
}
// Compute the interval; first <= last
years = last->year - first->year;
months = last->month - first->month;
days = last->day - first->day;
assert(years >= 0 && months >= 0 && days >= 0);
// Do obvious corrections (days before months!)
//
// This is a loop in case the previous month is
// February, and days < -28.
prev_month = last->month - 1;
while (days < 0)
{
// Borrow from the previous month
if (prev_month == 0)
prev_month = 12;
-months;
days += dtab[isleap(last->year)][prev_month-];
}
if (months < 0)
{
// Borrow from the previous year
-years;
months += 12;
}
// Return a date object with the interval
if (order == 1)
return Date(-months,-days,-years);
else
return Date(months,days,years);
}
int Date::compare(const Date& d2) const
{
int months, days, years, order;
years = year - d2.year;
months = month - d2.month;
days = day - d2.day;
// return <0, 0, or >0, like strcmp()
if (years == 0 && months == 0 && days == 0)
return 0;
else if (years == 0 && months == 0)
return days;
else if (years == 0)
return months;
else
return years;
}
ostream& operator<<(ostream& os, const Date& d)
{
os << d.month << '/' << d.day << '/' << d.year;
return os;
}
istream& operator>>(istream& is, Date& d)
{
char slash;
is >> d.month >> slash >> d.day >> slash >> d.year;
return is;
}
Date::Date()
(
// Get today's date
time_t tval = time(0);
struct tm *tmp= localtime(&tval);
month = tmp->tm_mon+1;
day = tmp->tm_mday;
year = tmp->tm_year + 1900;
}
// End of File
Listing 14 得到今天的日期
// tdate8.cpp:
#include <iostream.h>
#include "date8.h"
main()
{
Date today, d2;
cout << "Today's date is "<< today << endl;
cout << "Enter another date: ";
cin >> d2;
cout << "today - d2 = "<< today - d2 << endl;
cout << "d2 - today = "<< d2 - today << endl;
return 0;
}
/* OUTPUT
Today's date is 12/12/1992
Enter another date: 1/1/1970
today - d2 = 11/11/22
d2 - today = -11/-11/-22
*/
// End of File