当前位置: 首页 > news >正文

C++:日期类的实现

目录

一、前言

二、头文件

三、各个函数的实现

打印、检查日期及获取日期

=、+=、-=、-、+

==、<、<=、>、>=、 !=

日期-日期

>>、<<


一、前言

    前面几篇讲了关于类和对象的一些知识,本篇就来实现一下前面用到的日期类。

二、头文件

    先写上头文件,明确我们要实现哪些函数,还有一些实现函数需要用到的头文件,在头文件中定义日期类及其类中的函数。

#include<iostream>
using namespace std;
class date{friend ostream& operator<<(ostream& out, const date& d);friend istream& operator>>(istream& in, date& d);public:void Print();bool CheckDate();// 获取某年某月的天数int GetMonthDay(int year, int month);// 全缺省的构造函数date(int year = 1900, int month = 1, int day = 1){_year = year;_month = month;_day = day;}// 拷贝构造函数date(const date& d){_year = d._year;_month = d._month;_day = d._day;}// 赋值运算符重载date& operator=(const date& d);// 日期+=天数date& operator+=(int day);// 日期+天数date operator+(int day);// 日期-天数date operator-(int day);// 日期-=天数date& operator-=(int day);// 前置++date& operator++();// 后置++date operator++(int);// 后置--date operator--(int);// 前置--date& operator--();// >运算符重载bool operator>(const date& d);// ==运算符重载bool operator==(const date& d);// >=运算符重载bool operator >= (const date& d);// <运算符重载bool operator < (const date& d);// <=运算符重载bool operator <= (const date& d);// !=运算符重载bool operator != (const date& d);// 日期-日期 返回天数int operator-(const date& d);private:int _year;int _month;int _day;};
ostream& operator<<(ostream& out, const date& d);
istream& operator>>(istream& in, date& d);

   这里写日期类的流输入和流输出用到的是友元函数的方法,如果是写在类里面的话,由于类函数自带的(Date* this),在使用时和我们的流输入流输出的习惯会相反,就像这样

b>>a>>cout

这样的写法就会很别扭,所以这里是用到了友元函数的写法来解决这样的问题。

三、各个函数的实现

打印、检查日期及获取日期

    打印就是按照 年/月/日 这种形式来打印,检查日期是用来判断输入的日期是否有误,获取日期后面函数的实现基本都需要用到获取日期的功能,这里作为一个函数实现会方便很多。

void date::Print()
{cout<<_year<< "/" << _month <<"/"<< _day << endl;
}
bool date::CheckDate()
{if (_month<1 || _month>13 || _day < 0||_day>GetMonthDay(_year,_month))return false;elsereturn true;
}
int date::GetMonthDay(int year, int month)
{static int monthday[13] = { -1,31,28,31,30,31,30,31,31,30,31,30,31 };if (month == 2 && (year % 4 == 0 && year % 100 != 0) || (year % 400 == 0)){return 29;}elsereturn monthday[month];
}

    获取日期的函数这里再说一下,monthday数组给了13个元素是为了方便用的时候可以对应到我们的1到12月,第一个元素就随便写一个就行了,用来凑数的。

=、+=、-=、-、+

    这几个分别是日期的赋值、日期+=天数、日期+天数、日期-天数、日期-=天数

date& date::operator=(const date& d)
{_year = d._year;_month = d._month;_day = d._day;return *this;
}

    日期的赋值就是把单个的赋值改成年月日的赋值就行了。

date& date::operator+=(int day)
{if (day < 0){_day -= -day;return *this;}_day += day;while (_day > GetMonthDay(_year, _month)){_day -= GetMonthDay(_year, _month);++_month;if (_month == 13){_year++;_month = 1;}}return *this;
}

    前面用到-=的代码是为了解决给的天数为负数的问题,直接转换成-=计算,后面+=的逻辑就是先让年月日中的日的值加上我们给的天数,在进入一个循环,不断地判断日的值是否大于月的最大天数,如果大于就让月数+1,继续循环判断,直到日的值小于该月的最大天数,期间如果月份大于了13就给年份+1,月份从1月重新开始加,最后就会得到加完天数后的月份了。

date& date::operator-=(int day)
{if (day < 0){_day += -day;return *this;}_day -= day;while (_day <= 0){_month--;if (_month == 0){_year++;_month = 12;}_day += GetMonthDay(_year, _month);}return *this;
}

      -=也是类似的,前面避免给的天数为负值的情况,然后直接让日的值减去天数,进入循环,如果日的值为负数就要加上该月的最大天数,月份-1,直到日的值大于0,如过期间月份=0了就年份-1,月份从12月重新开始计算,最后得到日期。

date date::operator+(int day)
{date tem = *this;tem += day;return tem;
}
date date::operator-(int day)
{date tem = *this;tem -= day;return tem;
}

    有了前面的-=和+=,写-和+就可以直接套用了。

前置++、后置++、前置--、后置--

    在C++中为了区分++和--的前置和后置,后置的--和++是需要带参数的,这里需要注意一下。

date& date::operator++()
{*this += 1;return *this;
}
date date::operator++(int)
{date tem = *this;*this += 1;return tem;
}
date date::operator--(int)
{date tem = *this;*this -= 1;return tem;
}
date& date::operator--()
{*this -= 1;return *this;
}

    ++和--其实和前面的天数+-差不多,其实就是把给的day变成了1,这里也是直接套用前面的-=和+=,这里给的代码看一下,就不过多的解释了。

==、<、<=、>、>=、 !=

bool date::operator==(const date& d)
{return _year == d._year && _month == d._month && _day == d._month;
}

     判断两个日期是否相同比较一下年月日就行了,很简单。

bool date::operator < (const date& d)
{if (_year < d._year)return true;else if (_year == d._year){if (_month < d._month)return true;else if (_month == d._month){if (_day < d._day)return true;}}return false;
}

     比较两个日期的大小,先比较两个日期的年份,如果相等再比较月份,最后再比较天数就行了,也是比较简单的代码,这里写的<的,也就是左边的日期比右边的日期小就返回true,反之则是false,比较大小的逻辑,<和>是一样的。

bool date::operator <= (const date& d)
{return *this<d || *this==d;
}bool date::operator>(const date& d)
{return !(*this <= d);
}bool date::operator >= (const date& d)
{return !(*this < d);
}bool date::operator != (const date& d)
{return !(*this == d);
}

      后面的函数实现就可以套用前面两个函数,小于或者等于就是<=,不<=就是大于,不小于就是>=,否定相等相等就是!=,一环套一环还是挺有意思的不用写那么多代码。

日期-日期

    这个函数和前面的-不一样,前面的是日期-天数得到日期,这个是日期-日期得到天数

int date::operator-(const date& d)
{date max = *this;date min = d;int flag = 1;if (*this < d){max = d;min = *this;flag = -1;}int n = 0;while (min != max){min++;n++;}return n * flag;
}

      这个就是先把左边的日期定为大日期,右边的定为小日期,让小日期不断地++,直到和大日期相同为止,用一个变量记录,就可以得到差值,如果是右边的天数大,用到了一个flag的变量,就会返回负值。

>>、<<

ostream& operator<<(ostream& out, const date& d)
{out << d._year << "/" << d._month << "/" << d._day<<endl;return out;
}

     日期类的输出就是直接把对象的年月日输出就行了,这里的out就是cout的引用,返回cout是为了和原本的cout一样能输出多个对象。

istream& operator>>(istream& in, date& d)
{cout << "请按年月日依次输入日期:" << endl;in >> d._year >> d._month >> d._day;if (!d.CheckDate()){cout << "非法日期,请重新输入" << endl;cout << "请按年月日依次输入日期:" << endl;in >> d._year >> d._month >> d._day;}return in;
}

     日期类的输入也差不多,就是这里加了一个判断输入的日期是否合法,用到了前面日期检查的函数。


    本篇关于日期类的实现就到这里了,实现完后不要忘记了测试一下,好了,希望这篇内容对各位有帮助,如果有错误欢迎指出。

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 20240918 每日AI必读资讯
  • GEE教程:1950-2023年ECMWF数据中积雪的长时序统计分析
  • MySQL学习(视图总结)
  • 安卓将本地日志上传到服务器
  • 高效容器化技术(1)---容器化技术简介
  • 如何快速学习拼音打字?
  • Java程序流程控制
  • 基于Linux和C++实现的RabbitMQ风格消息队列:设计与实现
  • 第二届Apache Flink极客挑战赛冠军比赛攻略_SkyPeaceLL队
  • VirtualBox 7.1.0 发布下载 - 开源跨平台虚拟化软件
  • 大数据和代理:揭示它们之间的微妙联系
  • STM32 + W5500 实现HTTPS !
  • 从Profinet到Ethernet IP网关技术重塑工业网络,数据传输更流畅
  • Vue3 父组件向子组件传值:异步数据处理的显示问题
  • MiniDB 使用手册
  • [PHP内核探索]PHP中的哈希表
  • 【108天】Java——《Head First Java》笔记(第1-4章)
  • C# 免费离线人脸识别 2.0 Demo
  • - C#编程大幅提高OUTLOOK的邮件搜索能力!
  • export和import的用法总结
  • JAVA 学习IO流
  • Java 最常见的 200+ 面试题:面试必备
  • JS基础篇--通过JS生成由字母与数字组合的随机字符串
  • JS题目及答案整理
  • nodejs调试方法
  • SpingCloudBus整合RabbitMQ
  • vue2.0开发聊天程序(四) 完整体验一次Vue开发(下)
  • Vue全家桶实现一个Web App
  • Vue--数据传输
  • WinRAR存在严重的安全漏洞影响5亿用户
  • 百度地图API标注+时间轴组件
  • 编写高质量JavaScript代码之并发
  • 等保2.0 | 几维安全发布等保检测、等保加固专版 加速企业等保合规
  • 高程读书笔记 第六章 面向对象程序设计
  • 基于遗传算法的优化问题求解
  • 看图轻松理解数据结构与算法系列(基于数组的栈)
  • 如何优雅的使用vue+Dcloud(Hbuild)开发混合app
  • 收藏好这篇,别再只说“数据劫持”了
  • 新书推荐|Windows黑客编程技术详解
  • 一起参Ember.js讨论、问答社区。
  • 因为阿里,他们成了“杭漂”
  • 06-01 点餐小程序前台界面搭建
  • AI又要和人类“对打”,Deepmind宣布《星战Ⅱ》即将开始 ...
  • 好程序员web前端教程分享CSS不同元素margin的计算 ...
  • 浅谈sql中的in与not in,exists与not exists的区别
  • 专访Pony.ai 楼天城:自动驾驶已经走过了“从0到1”,“规模”是行业的分水岭| 自动驾驶这十年 ...
  • ​你们这样子,耽误我的工作进度怎么办?
  • ​人工智能书单(数学基础篇)
  • ​探讨元宇宙和VR虚拟现实之间的区别​
  • # 20155222 2016-2017-2 《Java程序设计》第5周学习总结
  • ###51单片机学习(2)-----如何通过C语言运用延时函数设计LED流水灯
  • #Datawhale X 李宏毅苹果书 AI夏令营#3.13.2局部极小值与鞍点批量和动量
  • #define,static,const,三种常量的区别
  • #define、const、typedef的差别
  • #LLM入门|Prompt#2.3_对查询任务进行分类|意图分析_Classification