9.C++面向对象6(实现一个较为完善的日期类)

⭐本篇重点:const成员变量和函数,取地址重载

⭐本篇代码:c++学习/02.c++面向对象-中/2.实现完善的日期类 · 橘子真甜/c++-learning-of-yzc - 码云 - 开源中国 (gitee.com)

目录

一. 日期类分析

二. 代码实现   

2.1 构造函数

2.2 拷贝构造

2.3 析构函数

2.4 赋值运算符重载

2.5 比较运算重载

2.6 加减法运算符重载

2.7 自增自减运算符重载

一. 日期类分析

        我们想要实现一个完善的日期类,首先要有基本的构造函数,析构函数,拷贝构造函数,赋值运算符重载。

        我们在日常生活中对日期的操作有,一个日期去加减某个天数获得另一个日期,比较两个日期(大于,小于,等于)。没有乘法除法(对于日期来说没有意义)

        根据分析,我们能够很快写出成员函数和成员变量的基本框架。

class Date
{
public://构造函数Date(int year = 0, int month = 0, int day = 0){}//析构函数~Date(){}//拷贝构造函数Date(const Date& d){}//赋值运算符重载Date& 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{}//大于等于bool operator>=(const Date& d)const{}//加减操作//加等Date& operator+=(int day){}//加Date& operator+(int day){}//减等Date& operator-=(int day){}//减Date& operator-(int day){}//前置++,++d1Date& operator++(){}//后置++,d1++,后置++我们在函数参数中用一个int进行标识,这是c++的约定Date& operator++(int){}//前置--,--d1Date& operator--(){}//后置--,d1--Date& operator--(int){}
private:int _year;int _month;int _day;
};

二. 代码实现   

2.1 构造函数

        我们知道一年有12个月,每个月都有自己的天数,那么用户输入的年,月,日就一定要合法。如果输入不合法就向用户显示报错。

        年份和月份都很好判断,年份:不是负数就行。月份:1<= m <=12。

        比较难判断的是日期,每月的天数不一样且有闰年存在,所以我们需要定义一个函数来获取某年某月的天数范围。

该函数代码如下:

	//获取某年某月的最大天数int GetMonthDay(const int& year, const int& month){static int MonthDays[13] = { 0,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;}return MonthDays[month];}

因此构造函数如下

//构造函数Date(int year = 0, int month = 0, int day = 0){if (year >= 0 && month >= 0 && month <= 12 && day <= GetMonthDay(year, month)){_year = year;_month = month;_day = day;}else{cout << "输入非法日期" << endl;_year = _month = _day = -999999;}}

2.2 拷贝构造

	//拷贝构造函数Date(const Date& d){_year = d._year;_month = d._month;_day = d._day;}

2.3 析构函数

无动态分配内存,不需要释放空间

//析构函数~Date(){}

2.4 赋值运算符重载

为了支持 d1 = d2 = d3这种操作,我们需要使用引用返回(见赋值运算符重载)

	//赋值运算符重载Date& operator=(const Date& d){if (this != &d)//this和d不同的情况下才能赋值{_year = d._year;_month = d._month;_day = d._day;}return *this;	//引用返回不能返回临时变量}

2.5 比较运算重载

小于

年份小一定小,年份相等,月份小一定小,年月相等,日小一定小

	//小于,定义为const函数bool operator<(const Date& d)const{if (_year < d._year)return true;else if (_year == d._year && _month < d._month)return true;else if (_year == d._year && _month == d._month && _day < d._day)return true;return false;}

等于

	//等于bool operator==(const Date& d)const{return _year == d._year && _month == d._month && _day == d._day;}

有了小于运算符重载和等于运算符重载,我们可以调用这个函数完成其他比较(函数复用)

小于等于

	//小于等于bool operator<=(const Date& d)const{return *this < d || *this == d;}

大于

	//大于bool operator>(const Date& d)const{return !(*this <= d);}

大于等于

	//大于等于bool operator>=(const Date& d)const{return !(*this < d);}

不等于

	//不等于bool operator!=(const Date& d)const{return !(*this == d);}

2.6 加减法运算符重载

加减法是用于两个日期相加吗??

2024/11/12 + 2024/11/13 没有意义所以我们实现的加减法都是一个日期去加减一个天数

如: 2024/11/12 + 1 

我们首先实现+=这个操作符和-=

        我们直接将合法day加入到这个日期的_day中,然后循环判断其值是否大于这年这月的天数,如果大于让其减去这个月的天数然后让_month++,如果_month大于12说明要进位年,_year++,_month-=12即可

+=

	//加等Date& operator+=(int day){if (day < 0){day -= (-1 * day);}else{_day += day;while (_day > GetMonthDay(_year, _month)){day -= GetMonthDay(_year, _month);_month++;if (_month >= 13){_month -= 12;_year++;}}}return *this;}

-=也是类似的思路

//减等Date& operator-=(int day){if (day > 0){day -= (-1 * day);}else{_day -= day;while (_day <= 0){_month--;if (_month == 0){_year--;//月份为0,说明年份要-1_month = 12;//月份回到早一年的12}_day += GetMonthDay(_year, _month);}}return *this;}

实现了+=和-=我们就能够用这两个重载去实现+和-        (实现对函数的复用)

+

注意不要使用引用返回!

	//加,这里不是使用引用返回是因为 d = d1+day 返回值应该是一个新创造的日期//如果使用引用返回,我们就会返回一个临时变量Date operator+(int day){Date ret = *this;ret += day; //本质是 ret.operator+(day);return ret;}

-

	//减Date operator-(int day){Date ret = *this;ret -= 1;return ret;}

2.7 自增自减运算符重载

d++

	//前置++,++d1,可以使用引用返回,减少拷贝Date& operator++(){*this += 1; //调用+=进行复用return *this;}

++d

	//后置++,d1++,后置++我们在函数参数中用一个int进行标识,这是c++的约定Date operator++(int){//后置++我们返回的是加1之前的值//所以我们不能使用引用返回Date tmp = *this;//保留加之前的值*this += 1;return tmp;//返回加之前的值}

--d

	//前置--,--d1Date& operator--(){*this -= 1;return *this;}

d--

	//后置--,d1--Date operator--(int){Date tmp = *this;//保留加之前的值*this -= 1;return tmp;//返回加之前的值}

至此一个完善的日期类就实现了,完整代码见Gitee

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/pingmian/61020.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

构建SSH僵尸网络

import argparse import paramiko# 定义一个名为Client的类&#xff0c;用于表示SSH客户端相关操作 class Client:# 类的初始化方法&#xff0c;接收主机地址、用户名和密码作为参数def __init__(self, host, user, password):self.host hostself.user userself.password pa…

199. 二叉树的右视图【 力扣(LeetCode) 】

文章目录 零、原题链接一、题目描述二、测试用例三、解题思路四、参考代码 零、原题链接 199. 二叉树的右视图 一、题目描述 给定一个二叉树的 根节点 root&#xff0c;想象自己站在它的右侧&#xff0c;按照从顶部到底部的顺序&#xff0c;返回从右侧所能看到的节点值。 二…

Mongo数据库集群搭建

目录 1、Mongo集群优势 1.1 高可用性 1.2 水平扩展性 1.3 高性能 1.4 灵活的架构设计 1.5 数据安全 1.6 管理与监控 2、下载指定操作系统版本包 3、部署和验证工作 3.1 准备配置文件及依赖 3.2 启动第一个节点 3.3 部署更多的节点 3.4 初始化副本集 3.5 设置管理…

DB Type

P位 p 1时段描述符有效&#xff0c;p 0时段描述符无效 Base Base被分成了三个部分&#xff0c;按照实际拼接即可 G位 如果G 0 说明描述符中Limit的单位是字节&#xff0c;如果是G 1 &#xff0c;那么limit的描述的单位是页也就是4kb S位 S 1 表示代码段或者数据段描…

Qt 5.6.3 手动配置 mingw 环境

- 安装 qt 5.6.3 mingw 版 - 打开 qt creator - 找到选项 工具 - 选项- 构建和运行 - 找到 “编译器” 选项卡 ,点击 "添加" “编译器路径” 设置为 qt 安装目录下&#xff0c; tool 文件夹内的 g.exe 设置完成后&#xff0c;点击 "apply" ,使选项生…

k8s上部署redis高可用集群

介绍&#xff1a; Redis Cluster通过分片&#xff08;sharding&#xff09;来实现数据的分布式存储&#xff0c;每个master节点都负责一部分数据槽&#xff08;slot&#xff09;。 当一个master节点出现故障时&#xff0c;Redis Cluster能够自动将故障节点的数据槽转移到其他健…

抖音热门素材去哪找?优质抖音视频素材网站推荐!

是不是和我一样&#xff0c;刷抖音刷到停不下来&#xff1f;越来越多的朋友希望在抖音上创作出爆款视频&#xff0c;但苦于没有好素材。今天就来推荐几个超级实用的抖音视频素材网站&#xff0c;让你的视频内容立刻变得高大上&#xff01;这篇满是干货&#xff0c;直接上重点&a…

Dify 通过导入 DSL 文件创建 Workflow 过程及实现

本文使用 Dify v0.9.2 版本&#xff0c;主要介绍 Dify 通过导入 DSL&#xff08;或 URL&#xff09;文件创建&#xff08;或导出&#xff09;Workflow 的操作过程及源码分析实现过程。Dify通过导入DSL文件创建Workflow过程及实现&#xff1a;https://z0yrmerhgi8.feishu.cn/wik…

代码随想录第46期 单调栈

这道题主要是单调栈的简单应用 class Solution { public:vector<int> dailyTemperatures(vector<int>& T) {vector<int> result(T.size(),0);stack<int> st;st.push(0);for(int i1;i<T.size();i){if(T[i]<T[st.top()]){st.push(i);}else{wh…

3步实现贪吃蛇

方法很简单&#xff0c;打开页面&#xff0c;复制&#xff0c;粘贴 一.整体思维架构 我们根据游戏的开始&#xff0c;运行&#xff0c;结束&#xff0c;将整个游戏划分成三个部分。在每个部分下面又划分出多个功能&#xff0c;接下来我们就根据模块一一实现功能。 二.Gamesta…

【linux012】文件操作命令篇 - more 命令

文章目录 more 命令1、基本用法2、常见选项3、交互式键盘命令4、举例5、注意事项 more 命令 more 是 Linux 中的一个分页查看命令&#xff0c;用于逐屏显示文件内容。它特别适合用于查看较长的文件&#xff0c;与 cat 不同&#xff0c;more 不会一次性输出所有内容&#xff0c…

机器学习笔记2 - 机器学习的一般流程

image.png 1、数据基本处理 数据集的划分 根据用途可将获取到的数据划分为训练集和测试集&#xff0c;有时还会有验证集。一般而言训练集用于训练模型&#xff0c;测试集用于测试模型的效果&#xff08;泛化误差&#xff09;。严格来讲&#xff0c;测试集的数据不能直接或间接&…

《C陷阱与缺陷》

文章目录 1、【词法陷阱】1.1 符号与组成符号间的关系1.1 与 1.3 y x/*p 与 y x/(*p)&#xff0c;a-1 与 a - 1 与 a -1, 老版本编译器的处理是不同的&#xff0c;严格的ANSI C则会报错1.4 十进制的 076&#xff0c;会被处理为八进制&#xff0c;ANSI C禁止这种用法&#x…

小白快速上手 labelme:新手图像标注详解教程

前言 本教程主要面向初次使用 labelme 的新手&#xff0c;详细介绍了如何在 Windows 上通过 Anaconda 创建和配置环境&#xff0c;并使用 labelme 进行图像标注。 1. 准备工作 在开始本教程之前&#xff0c;确保已经安装了 Anaconda。可以参考我之前的教程了解 Anaconda 的下…

脑机接口、嵌入式 AI 、工业级 MR、空间视频和下一代 XR 浏览器丨RTE2024 空间计算和新硬件专场回顾

这一轮硬件创新由 AI 引爆&#xff0c;或许最大受益者仍是 AI&#xff0c;因为只有硬件才能为 AI 直接获取最真实世界的数据。 在人工智能与硬件融合的新时代&#xff0c;实时互动技术正迎来前所未有的创新浪潮。从嵌入式系统到混合现实&#xff0c;从空间视频到脑机接口&…

【STM32】MPU6050简介

文章目录 MPU6050简介MPU6050关键块带有16位ADC和信号调理的三轴MEMS陀螺仪具有16位ADC和信号调理的三轴MEMS加速度计I2C串行通信接口 MPU6050对应的数据手册&#xff1a;MPU6050 陀螺仪加速度计 链接: https://pan.baidu.com/s/13nwEhGvsfxx0euR2hMHsyw?pwdv2i6 提取码: v2i6…

ISP——你可以从这里起步(二)

接上一篇&#xff0c;上一篇是原理篇&#xff0c;这一篇是实战篇&#xff0c;为了实现下面框图中的不完美ISP。 第一章 做一张RAW图自己用 不是所有的人都能获得raw图&#xff0c;即使获得了raw图也需要对应的sensor参数才能把它用起来&#xff0c;所以我找了一条野路子可以把…

Istio分布式链路监控搭建:Jaeger与Zipkin

分布式追踪定义 分布式追踪是一种用来跟踪分布式系统中请求的方法&#xff0c;它可以帮助用户更好地理解、控制和优化分布式系统。分布式追踪中用到了两个概念&#xff1a;TraceID 和 SpanID。 TraceID 是一个全局唯一的 ID&#xff0c;用来标识一个请求的追踪信息。一个请求…

【论文阅读】主动推理:作为感知行为的理论

文章目录 主动推理&#xff1a;作为感知行为的理论摘要1.引言2. 主动推理的概念和历史根源3. 主动推理的规范视角—以及它的发展历程 未完待续 主动推理&#xff1a;作为感知行为的理论 Active inference as a theory of sentient behavior 摘要 这篇文章综述了主动推理的历…

【MySQL】MySQL数据库入门:构建你的数据基石

&#x1f351;个人主页&#xff1a;Jupiter. &#x1f680; 所属专栏&#xff1a;MySQL初阶探索&#xff1a;构建数据库基础 欢迎大家点赞收藏评论&#x1f60a; 目录 &#x1f985;数据库基础&#x1f400;什么是数据库&#x1f40f;主流数据库&#x1f986;MySQL数据库的基本…