机械英文网站,找代加工产品哪个网,wordpress 相关帖子,vue使用于网站开发鼠鼠实现了一个日期类#xff0c;用来练习印证前几篇博客介绍的内容#xff01;#xff01; 目录
1.日期类的定义
2.得到某年某月的天数 3.检查日期是否合法 4.#xff08;全缺省#xff09;构造函数
5.拷贝构造函数
6.析构函数
7.赋值运算符重载
8.运算符重…鼠鼠实现了一个日期类用来练习印证前几篇博客介绍的内容 目录
1.日期类的定义
2.得到某年某月的天数 3.检查日期是否合法 4.全缺省构造函数
5.拷贝构造函数
6.析构函数
7.赋值运算符重载
8.运算符重载
9.运算符重载 10.运算符重载
11.运算符重载
12.运算符重载
13.!运算符重载
14.日期 天数
15.日期天数
16.日期-天数
17.日期-天数
18.前置
19.后置
20.前置--
21.后置--
22.日期-日期返回天数 23.流插入运算符重载
24.流提取运算符重载
25.test 本鼠创建一个工程工程包含三个文件分别是Date.h、Date.cpp和test.cpp。
1.日期类的定义
本鼠对日期类的定义如下放在了Date.h文件中
class Date
{int _year;int _month;int _day;
public:inline int GetMonth_day()const//得到某年某月的天数{const int a[13] { 0,31,28,31,30,31,30,31,31,30,31,30,31 };if (this-_month 2 (this-_year % 4 0 this-_year % 100 ! 0 || this-_year % 400 0)){return 29;}return a[this-_month];}bool Check()const;//检查日期是否合法Date(int year 1, int month 1, int day 1);//全缺省构造函数Date(const Date d);//拷贝构造函数~Date();//析构函数Date operator(const Date d)//赋值运算符重载{this-_year d._year;this-_month d._month;this-_day d._day;}bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator!(const Date d)const;//!运算符重载Date operator(int day);//日期天数Date operator(int day)const;//日期天数Date operator-(int day);//日期-天数Date operator-(int day)const;//日期-天数Date operator();//前置Date operator(int);//后置Date operator--();//前置--Date operator--(int);//后置--int operator-(const Date d)const;//日期-日期返回天数friend ostream operator(ostream cout, const Date d);//友元函数流插入运算符重载friend istream operator(istream cin, Date d);//友元函数流提取运算符重载
};
本鼠对于成员函数大部分都采取声明和定义分离的方式。成员变量无非就是年、月、日呗。还运用了友元的知识。如上代码所示。
2.得到某年某月的天数 对于这个日期类所要实现的成员函数中有很多场景我们需要得到某年某月的天数所以我们将这个功能实现成函数。又因为需要频繁调用这个函数我们将他实现成内联函数。
声明和定义
inline int GetMonth_day()const//得到某年某月的天数{const int a[13] { 0,31,28,31,30,31,30,31,31,30,31,30,31 };if (this-_month 2 (this-_year % 4 0 this-_year % 100 ! 0 || this-_year % 400 0)){return 29;}return a[this-_month];}
注意
该函数的实现思路过于简单本鼠就不解释了内联函数声明和定义不可分离又因为日期类的成员函数需频繁调用这个函数所以我们将其声明和定义都实现在类里面。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。 3.检查日期是否合法
例如构造函数可能构造了非法的日期所以我们将检查日期是否合法这个功能实现成函数。
定义
bool Date::Check()const//检查日期是否合法
{if (this-_year 0 ||this-_month 0 || this-_month 12 ||this-_day0 || this-_dayGetMonth_day()){return true;}return false;
}
注意
该函数的实现思路我们这个日期类不支持公元前的年份。所以当this指针指向对象的日期年小于0、月小于0、月大于12、日小于0、日大于该日期应得天数这几项但凡有一项为真时说明日期非法返回真否则返回假。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。 4.全缺省构造函数
我们分析日期类对象的初始化需求若使用编译器生成的默认构造函数是达不到需求的所以我们自己显式实现构造函数。
定义
Date::Date (int year , int month , int day )//全缺省构造函数
{this-_year year;this-_month month;this-_day day;if (Check()){cout 构造了日期非法 *this endl;}
}
注意
该函数的实现思路无非就是将第2、3、4个形参的年、月、日初始化this指针指向对象的成员变量年、月、日若形参没有接收到实参的拷贝使用缺省值。需要检查this指针指向对象的日期是否合法。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。缺省参数不能在函数声明和定义中同时出现当函数声明和定义分离时在声明给缺省参数 。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
5.拷贝构造函数
这个日期类不涉及资源申请其实不用我们显式实现拷贝构造函数用编译器生成的默认拷贝构造函数就行 本鼠显式实现就是练练手。
定义
Date::Date(const Date d)//拷贝构造函数
{this-_year d._year;this-_month d._month;this-_day d._day;
}
注意
该函数的实现思路第一个形参是隐藏的this指针第二个形参是已存在对象的引用。 用第二个形参的成员变量初始化this指针指向的正在创建对象的成员变量。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
6.析构函数
这个日期类的析构函数其实也不用我们自己显式实现的练练手。
定义
Date::~Date()//析构函数
{this-_year this-_month this-_day 0;
}
注意
不妨将this指针指向对象的成员变量赋值成0就行 其实函数体内为空也无妨。反正这个日期类没有申请资源当对象生命周期结束后系统会将其内存收归就行。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
7.赋值运算符重载
其实这个函数也不用我们自己显式实现的练练手。 声明和定义 Date operator(const Date d)//赋值运算符重载{this-_year d._year;this-_month d._month;this-_day d._day;return *this;}
注意
该函数实现思路第二个形参是已存在对象的引用。用第二个形参的成员变量赋值给this指针指向对象的成员变量就行。为了支持连续赋值需要返回左操作数本身拷贝也行。赋值运算符只能重载成类的成员函数不能重载成全局函数。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
8.运算符重载
定义
bool Date::operator(const Date d)const//运算符重载
{if (this-_year d._year){return true;}else if (this-_year d._year){if (this-_month d._month){return true;}else if (this-_month d._month){return this-_day this-_day;}}return false;
}
注意
该函数的第一个形参this指针为第一个操作数的地址第二个形参为第二个操作数的引用。该函数的实现思路若第一个操作数的年大于第二个操作数的年返回真若第一个操作数的年等于第二个操作数的年那就若第一个操作数的月大于第二个操作数的月返回真若第一个操作数的年和月都等于第二个操作数的年和月那就若第一个操作数的日大于第二个操作数的日返回真其余情况都返回假。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。
9.运算符重载
定义
bool Date::operator(const Date d)const//运算符重载
{return this-_year d._year this-_month d._month this-_day d._day;
}
注意 该函数的第一个形参this指针为第一个操作数的地址第二个形参为第二个操作数的引用。该函数实现思路第一个操作数的年、月、日都等于第二个操作数的年、月、日返回真否则返回假。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。 10.运算符重载
定义
bool Date:: operator(const Date d)const//运算符重载
{return *this d || *this d;
}
注意 该函数的第一个形参this指针为第一个操作数的地址第二个形参为第二个操作数的引用。该函数的实现思路若第一个操作数大于或者等于第二个操作数调用运算符重载和运算符重载返回真否则返回假。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。
11.运算符重载
定义
bool Date::operator(const Date d)const//运算符重载
{return !(*this d);
} 注意
该函数的第一个形参this指针为第一个操作数的地址第二个形参为第二个操作数的引用。该函数的实现思路返回运算符重载的逻辑取反就好。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。
12.运算符重载
定义
bool Date::operator(const Date d)const//运算符重载
{return !(*this d);
}注意
该函数的第一个形参this指针为第一个操作数的地址第二个形参为第二个操作数的引用。该函数的实现思路返回运算符重载的逻辑取反就好。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。
13.!运算符重载
定义
bool Date::operator!(const Date d)const//!运算符重载
{return !(*this d);
}
注意
该函数的第一个形参this指针为第一个操作数的地址第二个形参为第二个操作数的引用。该函数的实现思路返回运算符重载的逻辑取反就好。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。
14.日期 天数
这个函数本鼠想要的是日期天数后日期本身发生改变形成新日期并返回。
定义
Date Date::operator(int day) //日期 天数
{this-_day day;while (this-_day GetMonth_day()){this-_day - GetMonth_day();this-_month;if (this-_month 12){this-_month 1;this-_year;}}return *this;
}
注意
该函数的实现思路 this指针指向对象的日期的日天数。循环日若超过“当年当月”该有的天数说明月该1就让日-“当年当月”该有的天数并月若是月超过12年份就该1…………直到日小于“当年当月”该有的天数循环停止。思想本质就跟我们做加法运算是一样的有时又要向高位进位。。该函数的返回值*this出了该函数作用域还存在可以用引用返回。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
15.日期天数
这个函数本鼠想要的是日期天数后日期本身不发生改变却要返回日期天数后的结果。
定义
Date Date::operator(int day)const//日期天数
{Date tmp *this;tmp day;return tmp;
}
注意
该函数的实现思路通过拷贝构造函数创建一个与this指针指向对象一样的临时对象让临时对象天数返回临时对象就好了。该函数的返回值是临时对象出了该函数的作用域就不存在了所以不能用引用返回。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。
16.日期-天数
这个函数本鼠想要的是日期-天数后日期本身发生改变形成新日期并返回。
定义
Date Date::operator-(int day)//日期-天数
{this-_day - day;while (this-_day 0){this-_month--;if (this-_month 1){this-_year--;this-_month 12;}this-_day GetMonth_day();}return *this;
}
注意
该函数的实现思路this指针指向对象的日-天数。循环日若小于或等于0说明月该-1月--后需要判断月是否小于1如果月小于1年份就该-1日“当年当月”该有的天数…………直到日大于0循环停止。思想本质跟我们做减法运算是一样的有时候要跟高位借位呗。。该函数的返回值*this出了该函数作用域还存在可以用引用返回。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
17.日期-天数
这个函数本鼠想要的是日期-天数后日期本身不发生改变却要返回日期-天数后的结果。
定义
Date Date::operator-(int day)const//日期-天数
{Date tmp *this;tmp - day;return tmp;
}
该函数的实现思路通过拷贝构造函数创建一个与this指针指向对象一样的临时对象让临时对象-天数返回临时对象就好了。该函数的返回值是临时对象出了该函数的作用域就不存在了所以不能用引用返回。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。
18.前置
前置日期本身1返回日期1之后的结果。
定义
Date Date::operator()//前置
{*this 1;return *this;
}
注意
这个函数实现思想过于简单不解释了。 该函数的返回值*this出了该函数作用域还存在可以用引用返回。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
19.后置
后置先使用后1因此需要返回1之前的旧值。日期本身1返回日期1之前的旧日期。
定义
Date Date::operator(int)//后置
{Date tmp *this;*this 1;return tmp;
}
注意
这个函数实现思想过于简单不解释。后置重载时多增加一个int类型的参数不显式调用函数时该参数不用传递编译器自动传递显式调用该函数那么一定要传入一个任意int整形以区分前置。这个函数的返回值是临时变量出了该函数作用域就不存在了所以不能用引用返回。 该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
20.前置--
前置--日期本身-1返回日期-1之后的结果。
定义
Date Date::operator--()//前置--
{*this - 1;return *this;
}
注意
这个函数实现思想过于简单不解释了。 该函数的返回值*this出了该函数作用域还存在可以用引用返回。该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
21.后置--
后置--先使用后-1因此需要返回-1之前的旧值。日期本身-1返回日期-1之前的旧日期。
定义
Date Date::operator--(int)//后置--
{Date tmp *this;*this - 1;return tmp;
}
注意
这个函数实现思想过于简单不解释。后置--重载时多增加一个int类型的参数不显式调用函数时该参数不用传递编译器自动传递显式调用该函数那么一定要传入一个任意int整形以区分前置--。这个函数的返回值是临时变量出了该函数作用域就不存在了所以不能用引用返回。 该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量要进行读写访问的成员函数不能实现成const成员函数。
22.日期-日期返回天数
这个函数本鼠想要获取日期之间夹杂着多少天呗。如果第一个日期大于第二个日期返回的天数是负数反之为正数。
定义
int Date::operator-(const Date d)const//日期-日期返回天数
{Date max *this;Date min d;int flag -1;if (max min){flag 1;max d;min *this;}int n 0;while (max ! min){min;n;}return n * flag;
}
注意
这个函数实现思路简单本鼠就不解释了。 该函数声明和定义分离所以定义成员函数时成员函数名前需要加Date::成员函数定义在Date.cpp文件中。这是一个对this指针指向对象的成员变量只进行读访问的函数所以我们将其实现成const成员函数。 23.流插入运算符重载
介绍流插入运算符重载之前我们需要回顾这里C的输入输出介绍过的知识cout是库里面的ostream类型的全局对象。
对于流插入运算符重载本鼠并没有将其重载成日期类的成员函数而是重载成全局函数为啥 我们先看流插入运算符一般的使用场景如下
#includeiostream
using namespace std;
int main()
{int a 10;int b 20;cout a b endl;return 0;
} 我们分析
分析1对于流插入操作符来说是有两个操作数的第一个应该对象cout第二个是需要“流向”控制台的对象。 分析2流插入操作符需要支持连续输出如这里 cout a b endl; 这句语句的结合性是从左往右的couta的返回值是对象cout这个返回值cout又作为cout 的左操作数cout 的返回值又是对象cout这个返回值cout又作为coutb的左操作数………… 如果我们将流插入运算符重载重载成日期类的成员函数的话我们想想当我们在主函数调用的情景必然是这样的
int main()
{Date d1;d1.operator(cout);//显式调用d1. cout;//不显式调用return 0;
}
可是这样子的话代码的可读性不好好像是cout通过“流向” d1一样。不符合我们对分析1的分析。 那该如何是好呢其中一个办法就是将流插入运算符重载重载成全局函数。
那么将其重载成全局函数的话也采用声明和定义分离为了支持连续输出返回值应该是对象cout。
声明声明在Date.h文件中
ostream operator(ostream cout, const Date d);//流插入运算符重载
定义定义在Date.cpp文件中
ostream operator(ostream cout, const Date d)//流插入
{cout d._year / d._month / d._day ;return cout;
}
我们没有将其重载成全局函数日期类的成员变量又是被访问限定符private修饰的那么在这个全局函数中无权访问对象的成员变量啊。所以我们在日期类中用到友元函数
friend ostream operator(ostream cout, const Date d);//友元函数流插入运算符重载
24.流提取运算符重载 介绍流提取运算符重载之前我们需要回顾这里C的输入输出介绍过的知识cin是库里面的istream类型的全局对象。
流提取运算符重载的问题和流插入运算符重载的问题差不多不介绍了。
流提取运算符重载重载成全局函数采取声明和定义分离为了支持连续输入返回值应该是对象cin。
声明声明在Date.h文件中
ostream operator(ostream cout, const Date d);//流插入运算符重载
定义定义在Date.cpp文件中
istream operator(istream cin, Date d)//流提取{cout 请输入日期并以回车键结束 endl;while (1){cin d._year d._month d._day;if (d.Check()){cout 输入日期非法 endl;}else{break;}}return cin;}
不同的是这里流提取可以给一定的提示如请输入日期并以回车键结束。检查输入的日期是否合法也是必须的。
日期类中用到友元函数
friend istream operator(istream cin, Date d);//友元函数流提取运算符重载
25.test 全部代码如下可以在test.cpp中测试代码有兴趣可以玩玩。
Date.h:
#pragma once
#includestdbool.h
#includeiostream
using namespace std;
class Date
{int _year;int _month;int _day;
public:inline int GetMonth_day()const//得到某年某月的天数{const int a[13] { 0,31,28,31,30,31,30,31,31,30,31,30,31 };if (this-_month 2 (this-_year % 4 0 this-_year % 100 ! 0 || this-_year % 400 0)){return 29;}return a[this-_month];}bool Check()const;//检查日期是否合法Date(int year 1, int month 1, int day 1);//全缺省构造函数Date(const Date d);//拷贝构造函数~Date();//析构函数Date operator(const Date d)//赋值运算符重载{this-_year d._year;this-_month d._month;this-_day d._day;return *this;}bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator(const Date d)const;//运算符重载bool operator!(const Date d)const;//!运算符重载Date operator(int day);//日期天数Date operator(int day)const;//日期天数Date operator-(int day);//日期-天数Date operator-(int day)const;//日期-天数Date operator();//前置Date operator(int);//后置Date operator--();//前置--Date operator--(int);//后置--int operator-(const Date d)const;//日期-日期返回天数friend ostream operator(ostream cout, const Date d);//友元函数流插入运算符重载friend istream operator(istream cin, Date d);//友元函数流提取运算符重载
};ostream operator(ostream cout, const Date d);//流插入运算符重载istream operator(istream cin, Date d);//流提取运算符重载
Date.cpp
#includeDate.h
bool Date::Check()const//检查日期是否合法
{if (this-_year 0 ||this-_month 0 || this-_month 12 ||this-_day0 || this-_dayGetMonth_day()){return true;}return false;
}Date::Date (int year , int month , int day )//全缺省构造函数
{this-_year year;this-_month month;this-_day day;if (Check()){cout 构造了日期非法 *this endl;}
}Date::Date(const Date d)//拷贝构造函数
{this-_year d._year;this-_month d._month;this-_day d._day;
}Date::~Date()//析构函数
{this-_year this-_month this-_day 0;
}bool Date::operator(const Date d)const//运算符重载
{if (this-_year d._year){return true;}else if (this-_year d._year){if (this-_month d._month){return true;}else if (this-_month d._month){return this-_day this-_day;}}return false;
}bool Date::operator(const Date d)const//运算符重载
{return this-_year d._year this-_month d._month this-_day d._day;
}bool Date:: operator(const Date d)const//运算符重载
{return *this d || *this d;
}bool Date::operator(const Date d)const//运算符重载
{return !(*this d);
}bool Date::operator(const Date d)const//运算符重载
{return !(*this d);
}bool Date::operator!(const Date d)const//!运算符重载
{return !(*this d);
}Date Date::operator(int day) //日期 天数
{this-_day day;while (this-_day GetMonth_day()){this-_day - GetMonth_day();this-_month;if (this-_month 12){this-_month 1;this-_year;}}return *this;
}Date Date::operator(int day)const//日期天数
{Date tmp *this;tmp day;return tmp;
}Date Date::operator-(int day)//日期-天数
{this-_day - day;while (this-_day 0){this-_month--;if (this-_month 1){this-_year--;this-_month 12;}this-_day GetMonth_day();}return *this;
}Date Date::operator-(int day)const//日期-天数
{Date tmp *this;tmp - day;return tmp;
}Date Date::operator()//前置
{*this 1;return *this;
}Date Date::operator(int)//后置
{Date tmp *this;*this 1;return tmp;
}Date Date::operator--()//前置--
{*this - 1;return *this;
}Date Date::operator--(int)//后置--
{Date tmp *this;*this - 1;return tmp;
}int Date::operator-(const Date d)const//日期-日期返回天数
{Date max *this;Date min d;int flag -1;if (max min){flag 1;max d;min *this;}int n 0;while (max ! min){min;n;}return n * flag;
}ostream operator(ostream cout, const Date d)//流插入
{cout d._year / d._month / d._day ;return cout;
}istream operator(istream cin, Date d)//流提取{cout 请输入日期并以回车键结束 endl;while (1){cin d._year d._month d._day;if (d.Check()){cout 输入日期非法请重新输入 endl;}else{break;}}return cin;}
test.cpp
#includeDate.h
int main()
{Date d1(2003, 12, 12);Date d2 d1;cout d1 endl d2 endl;cout (d1 d2) endl;cout (d1 d2) endl;cout (d1 d2) endl;cout (d1 d2) endl;cout (d1 d2) endl;cout (d1 ! d2) endl;Date d3;cout d3 endl;cin d3 d2 d1;cout d3 endl d2 endl d1 endl;return 0;
} 运行结果符合预期 感谢阅读