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

C++日期类实现

一、date.h文件(声明)

#pragma once
#include<iostream>
using namespace std;class Date
{friend ostream& operator<<(ostream& out, const Date& d);//友元函数声明(可以让类外的函数访问成员变量)friend istream& operator>>(istream& in,  Date& d);//友元函数声明(可以让类外的函数访问成员变量)
public:// 获取某年某月的天数int GetMonthDay(int year, int month);// 全缺省的构造函数Date(int year = 1900, int month = 1, int day = 1); //全缺省函数,声明时给缺省值,定义函数不要给// 拷贝构造函数// d2(d1)Date(const Date& d);// 赋值运算符重载// d2 = d3 -> d2.operator=(&d2, d3)Date& operator=(const Date& d);// 析构函数~Date();// 日期+=天数Date& operator+=(int day);// 日期+天数Date operator+(int day);// 日期-天数Date operator-(int day);// 日期-=天数Date& operator-=(int day);// 前置++Date& operator++();// 为了区分,构成重载,给后置++,强⾏增加了⼀个int形参
// 这⾥不需要写形参名,因为接收值是多少不重要,也不需要⽤
// 这个参数仅仅是为了跟前置++构成重载区分// 后置++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);void Print();private:int _year;int _month;int _day;};

二、add.cpp文件(定义)

#include"date.h"// 获取某年某月的天数
int Date::GetMonthDay(int year, int month)
{static int arr[13] = { -1,31,28,31,30,31,30,31,31,30,31,30,31 };//静态数组//如果是闰年的2月份,2月份多一天if ((month == 2) && ((year % 4 == 0 && year % 100 != 0) || year % 400 == 0))return 29;return arr[month];//返回某年某月的天数
}// 全缺省的构造函数
Date::Date(int year , int month , int day )//全缺省函数,声明时给缺省值,定义函数时不要给
{_year = year;_month = month;_day = day;
}// 拷贝构造函数
// d2(d1)
Date::Date(const Date& d)
{_year = d._year;_month = d._month;_day = d._day;
}// 赋值运算符重载
// d2 = d3 -> d2.operator=(&d2, d3)
Date& Date:: operator=(const Date& d)
{if (*this != d)//防止给本身赋值{_year = d._year;_month = d._month;_day = d._day;}return *this; //d1=d2的返回值是d1,也就是*this
}// 析构函数
Date::~Date()
{_year = 0;_month = 0;_day = 0;
}// 日期+=天数
Date& Date:: operator+=(int day)//日期自己本身需要改变
{_day += day;int n= GetMonthDay(_year, _month);//得到该月的天数while (_day > n) //如果加到的总天数大于该月的总天数,就要跳到下一个月{if (_month == 12)//如果是12月,加一个月,就到了下一年的一月{_year += 1;_month = 1;}else_month += 1;//月数加1_day -= n;n = GetMonthDay(_year, _month);//更新到下一个月的天数}return *this;
}// 日期+天数
Date Date::operator+(int day)//日期自己本身不需要改变
{//方法1:附用+=运算符(方便)Date temp(*this);拷贝构造一个临时变量,改变这个临时变量的值temp += day;// 附用-=运算符重载return temp;//方法2:不附用+=运算附(不方便)//Date temp(*this);//拷贝构造一个临时变量,改变这个临时变量的值//temp._day += day;//int n = GetMonthDay(temp._year, temp._month);//得到该月的天数//while (temp._day > n) //如果加到的总天数大于该月的总天数,就要跳到下一个月//{//	if (temp._month == 12)//如果是12月,加一个月,就到了下一年的一月//	{//		temp._year += 1;//		temp._month = 1;//	}//	else//		temp._month += 1;//月数加1//	temp._day -= n;//	n = GetMonthDay(temp._year, temp._month);//更新到下一个月的天数//}//return temp;
}// 日期-天数
Date Date::operator-(int day)//日期自己本身不需要改变
{Date temp(*this);拷贝构造一个临时变量,改变这个临时变量的值temp -= day;// 附用-=运算符重载return temp;
}日期-=天数
Date& Date::operator-=(int day)//日期自己本身需要改变
{_day -= day;int n ;//得到该月的天数while (_day<=0) //如果减到的值大于0,就不需改变年和月,小于0就要改变月(可能改变年){if (_month == 1)//如果是1月,减一个月,就到了前一年的12月{_year -= 1;_month = 12;}else_month -= 1;//月数减1n = GetMonthDay(_year, _month);//更新到前一个月的天数_day =  _day + n;}return *this;
}// 前置++
Date& Date::operator++()//返回++后的值
{*this += 1;//附用+=运算符重载return *this;
}// 后置++
Date Date::operator++(int)//返回++前的值
{Date temp(*this);//拷贝构造一个临时变量*this += 1;//附用+=运算符重载return temp;
}// 后置--
Date Date::operator--(int)//返回--前的值
{Date temp(*this);//拷贝构造一个临时变量*this -= 1;//附用-=运算符重载return temp;
}// 前置--
Date& Date::operator--()//返回--后的值
{*this -= 1;//附用-=运算符重载return *this;
}// 日期-日期 返回天数
int Date:: operator-(const Date& d)//从小的日期开始,每次都加1天,总计一共加了多少天,就是日期的差值
{Date max = *this;//假设法Date min = d;int flag = 1;if (*this < d) //相差负数天(被减数小于减数){max = d;min = *this;flag = -1;}int i = 0;while (min < max){min++;i ++ ;}return i*flag;
}// ==运算符重载
bool Date::operator==(const Date& d)
{if (_year == d._year && _month == d._month && _day == d._day)return true;elsereturn false;
}// >运算符重载
bool Date::operator>(const Date& d)
{if (   (_year > d._year)||( (_year==d._year)&&(_month>d._month) )|| ((_year == d._year) && (_month == d._month)&&(_day>d._day))   )  return true;elsereturn false;
}// >=运算符重载
bool Date::operator >= (const Date& d)
{if (!operator<(d))//如果不小于,则是大于等于return true;elsereturn false;
}// <运算符重载
bool Date::operator < (const Date& d)
{if ((_year < d._year) || ((_year == d._year) && (_month < d._month)) ||((_year == d._year) && (_month == d._month) && (_day < d._day)))return true;elsereturn false;
}// <=运算符重载
bool Date::operator <= (const Date& d)
{if (!operator>(d))//如果不大于,则是小于等于return true;elsereturn false;
}// !=运算符重载
bool Date::operator != (const Date& d)
{if(operator==(d))//附用判断相等的函数。如果相等,说明不相等//if (*this == d)return false;elsereturn true;
}void Date::Print()
{cout << _year << '/' << _month << '/' << _day << endl;
}ostream& operator<<( ostream& out,const Date&d )//输出函数
{out << d._year << "年" << d._month << "月" << d._day << "日" << endl;return out;  //返回值是ostream类型的引用,使得它可以连续输出
}istream& operator>>(istream& in,  Date& d)//输入函数{cout << "请依次输入年月日" << endl;in>>d._year >> d._month >> d._day;return in;  //返回值是istream类型的引用,使得它可以连续输入}

三、test.cpp文件(测试)

#include"date.h"int main()
{Date d1(2024, 11, 1);Date d2(1778, 11, 1);Date d4(1, 1, 1);cout << d1 << d2 << d4 << endl;Date d5;cout << d5 << endl;cin >> d5;cout << d5 << endl;//d1.Print();//d2.Print();//d3.Print();//d4.Print();//printf("\n");//d1 = d2 = d3 = d4;//d1.Print();//d2.Print();//d3.Print();//d4.Print();/*int n = d2 - d1;printf("%d", n);*///d1.Print();//Date d2 = d1--;//d2.Print();//d1.Print();//d1 -= 10;//Date d1(2024, 9,30);//d1.Print();//Date d2=++d1;//d2.Print();d1 -= 10;//d1.Print();/*Date d5 = d1 +100000;d1.Print();d5.Print();*//*Date d2(2024, 10, 1);d2.Print();d2 -= 100000;d2.Print();*///Date d3 = d2;//赋值拷贝(因为这里d3这个类,正在被创建,所以是赋值拷贝//d3.Print();//Date d4(d2);//赋值拷贝//d4.Print();//d4 = d1;//这里是赋值运算符重载,因为d4和d1都是已经存在的类//d4.Print();return 0;
}

相关文章:

  • 【Python语言初识(五)】
  • linux修改命令别名的方式
  • 前端大模型入门:Transformer.js 和 Xenova-引领浏览器端的机器学习变革
  • ——快速排序
  • SpringCloud Gateway 打印请求响应日志、跨域全局配置
  • 2024!再见前端!
  • 网络编程(8)+字节序处理
  • Redis 五大基本数据类型及其应用场景进阶(缓存预热、雪崩 、穿透 、击穿)
  • SpringCloud-Netflix第一代微服务快速入门
  • u盘拷贝文件管控怎么设置?禁止往U盘拷贝文件的8种方法!(图文详解)
  • Java面试题真题·人才招聘系统项目介绍
  • autogen改变屏幕亮度
  • VMware搭建DVWA靶场
  • 【Vue】为什么 Vue 不使用 React 的分片更新?
  • 如何提升网页加载和跳转速度:Flask 模板渲染 vs Nginx 静态资源处理
  • 收藏网友的 源程序下载网
  • 2017-09-12 前端日报
  • Docker入门(二) - Dockerfile
  • express.js的介绍及使用
  • Hibernate最全面试题
  • JS函数式编程 数组部分风格 ES6版
  • Netty+SpringBoot+FastDFS+Html5实现聊天App(六)
  • React系列之 Redux 架构模式
  • Redis 中的布隆过滤器
  • vue+element后台管理系统,从后端获取路由表,并正常渲染
  • vue中实现单选
  • 多线程事务回滚
  • 聊聊sentinel的DegradeSlot
  • 深度解析利用ES6进行Promise封装总结
  • 一个项目push到多个远程Git仓库
  • 走向全栈之MongoDB的使用
  • 阿里云重庆大学大数据训练营落地分享
  • 数据库巡检项
  • ‌JavaScript 数据类型转换
  • %@ page import=%的用法
  • (+4)2.2UML建模图
  • (Java企业 / 公司项目)点赞业务系统设计-批量查询点赞状态(二)
  • (附源码)c#+winform实现远程开机(广域网可用)
  • (七)Knockout 创建自定义绑定
  • (四)Linux Shell编程——输入输出重定向
  • (转)socket Aio demo
  • (转)关于pipe()的详细解析
  • (转载)虚幻引擎3--【UnrealScript教程】章节一:20.location和rotation
  • (轉貼)《OOD启思录》:61条面向对象设计的经验原则 (OO)
  • .NET Core 中的路径问题
  • .net dataexcel 脚本公式 函数源码
  • .NET/C# 反射的的性能数据,以及高性能开发建议(反射获取 Attribute 和反射调用方法)
  • .Net8 Blazor 尝鲜
  • .NET使用存储过程实现对数据库的增删改查
  • .Net语言中的StringBuilder:入门到精通
  • .stream().map与.stream().flatMap的使用
  • @FeignClient 调用另一个服务的test环境,实际上却调用了另一个环境testone的接口,这其中牵扯到k8s容器外容器内的问题,注册到eureka上的是容器外的旧版本...
  • @kafkalistener消费不到消息_消息队列对战之RabbitMq 大战 kafka
  • [ 隧道技术 ] 反弹shell的集中常见方式(四)python反弹shell
  • [@Controller]4 详解@ModelAttribute