天天看點

日期類與時間類定義(運算符重載應用)

文章目錄

      • 日期類與時間類定義(運算符重載應用)
        • 日期類定義(運算符重載應用):
        • 時間類定義(運算符重載應用):

日期類與時間類定義(運算符重載應用)

日期類定義(運算符重載應用):

class Data     //起初隻是用來表示出版日期,後來發現借閱與歸還日期都可用
{
    int year;
    int month;
    int day;
public:
    Data(){};
    Data(int year1,int month1,int day1):year(year1),month(month1),day(day1){};
    friend ostream&operator<<(ostream&os,const Data&d);
    friend istream&operator>>(istream&is,Data&d);
    bool operator<(const Data &d)const    //日期比較函數
    {return year!=d.year?year<d.year:month!=d.month?month<d.month:day<d.day;}
    int operator-(Data d)  //對日期的操作,可以直接按月份進行兩個月的相減操作,也可以按如下方式進行精确一點的操作(還可以判斷平年閏年進行更精确的操作)
	{
	    if(year<d.year||(year==d.year&&month<d.month)||(year==d.year&&month==d.month&&day<d.day))
            return -1;  //當日期沒有辦法相減(後面的日期大時)
        int m[13] = {0,31,28,31,30,31,30,31,31,30,31,30,31};  //按下标(對應月份)補齊,第一個數不計,對于每年的二月按28天計(不考慮平年閏年)
	    int count=0;
	    int a=d.year,b=d.month,c=d.day;
	    while(1)
	    {
            if(this->year==a&&this->month==b&&this->day==c) break;
	        if(c==m[b]){
                c=1;
                if(b==12)
                 {
                     b=1;
                     a++;
                 }
                 else b++;
	        }
	        else c++;
	        count++;
        }
	        return count;
	}
	Data operator+ (int x)
	{
        int m[13] = {0,31,28,31,30,31,30,31,31,30,31,30,31};  //按下标(對應月份)補齊,第一個數不計,對于每年的二月按28天計(不考慮平年閏年)
        while(x--)
        {
            if(day==m[month])
            {
                day=1;
                if(month==12)
                {
                    year++;
                    month=1;
                }
                else month++;
            }
            else day++;
        }
        return *this;
	}
};

istream&operator>>(istream&is,Data&d)    //先重載出版日期的輸入輸出
{
    while(1)
    {
        is>>d.year>>d.month>>d.day;
        if(d.year<1900||d.year>2019||d.month<1||d.month>12||d.day<1||d.day>31); //這裡可以優化為判斷閏年或平年然後進行判斷
        else break;
    }
    return is;
}
ostream&operator<<(ostream&os,const Data&d)
{
    //os<<"year:"<<d.year<<" "<<"month:"<<d.month<<" "<<"day:"<<d.day;
    //為了輸入輸出相統一,改為下面的輸出形式
    os<<d.year<<" "<<d.month<<" "<<d.day;
    return os;
}
           

時間類定義(運算符重載應用):

class Time
{
    int year,month,day,hour,min;
    string s;
public:
    Time() {};
    ~Time() {};
    Time(int year1,int month1 ,int day1,int hour1,int min1):year(year1),month(month1),day(day1),hour(hour1),min(min1) {};
    friend istream& operator>>(istream&,Time&t);
    friend ostream& operator<< (ostream&,const Time&t);
    int operator- (Time t)  //重載運算符"-"在類内定義,類外定義由于year,month等是私有的,需使用get函數擷取資料,沒有必要
    {   //直接定義即可,不必使用引用,一開始覺得都一樣,使用了引用,後來發現錯誤沒法調了,調了很久才發現,使用引用後減号後面的值會變為減号前的值,兩個值就一樣了
        if((year<t.year)||(year==t.year&&month<t.month)||(year==t.year&&month==t.month&&day<t.day)||(year==t.year&&month==t.month&&day==t.day&&hour<t.hour)||year==t.year&&month==t.month&&day==t.day&&hour==t.hour&&min<t.min)
        return -1;
        int countyear=0;
        int countmonth=0;
        int countday=0;
        int counthour=0;
        int countmin=0;
        int m[13] = {0,31,28,31,30,31,30,31,31,30,31,30,31};  //按下标(對應月份)補齊,第一個數不計,對于每年的二月按28天計(不考慮平年閏年)
        while(1)
	    {
            if(this->year==t.year&&this->month==t.month&&this->day==t.day&&hour==t.hour&&min==t.min) break;
	        if(t.min==60)
	        {
	            t.hour++;
	            counthour++;
	            t.min=0;
                if(t.hour==24)
                {
                    t.day++;
                    countday++;
                    t.hour=0;
                    if(t.day>m[t.month])  //上述日期末尾天數是存在的,如果寫"==",則直接跳過,不符實際
                    {
                        t.month++;
                        countmonth++;
                        t.day=1;
                        if(t.month>12)    //12月是存在的
                        {
                            t.year++;
                            countyear++;
                            t.month=1;
                        }
                    }
                }
	        }
	        else {t.min++;countmin++;}
        }
        //cout<<countyear<<" "<<countmonth<<" "<<countday<<" "<<counthour<<" "<<countmin<<endl;
        return countmin;
    }
    //Time operator+ (int i);  //利用"-"操作可以代替"+"
    //對于時間的比較,一開始不打算用的,不過後面的登入以及對使用者對待出行車票的檢視都需要用到
    bool operator< (const Time&t)const
    {
        return year!=t.year?year<t.year:month!=t.month?month<t.month:day!=t.day?day<t.day:hour!=t.hour?hour<t.hour:min<t.min;
    }
    bool operator== (const Time&t)const
    {
        return year==t.year&&month==t.month&&day==t.day&&hour==t.hour&&min==t.min;
    }
};

istream&operator>>(istream&in,Time&t)
{
    while(1)  //使用循環也好也不好,當程式運作時使用者輸入時間可以重新輸入,但當檔案内的時間有誤時,程式會一直循環
    {
        //in>>t.year>>t.s>>t.month>>t.s>>t.day>>t.s>>t.hour>>t.s>>t.min;
        in>>t.year>>t.month>>t.day>>t.hour>>t.min;
        if(t.year>2000&&t.year<=2019&&t.month>=1&&t.month<=12&&t.day>=1&&t.day<=31&&t.hour>=0&&t.hour<=23&&t.min>=0&&t.min<60)   //對時間進行限制,還應注意過時車票不可買(查詢也不可查,這可以在登入時間上作要求)
        break;
        else cout<<"Time error,請重試:"<<endl;
    }
    return in;
}

ostream&operator<<(ostream&out,const Time&t)
{
    out<<t.year<<" "<<t.month<<" "<<t.day<<" "<<t.hour<<" "<<t.min;
    return out;
}
           
c++

繼續閱讀