C++设计一:日期类Date实现

一、引言与概述

1 引言

日期操作是软件开发中的常见需求,如日程管理、数据统计等场景均需处理日期的比较、偏移及合法性校验。为简化此类操作,本文设计了一个高效且类型安全的C++日期类Date

该类通过构造函数内嵌合法性检查,确保对象初始状态的正确性;借助运算符重载,用户可直观使用d1 > d2d += 30等语法进行逻辑判断与日期计算,显著提升代码可读性。内部方法GetMonthDay结合静态数组与闰年规则,动态适配不同月份的天数变化,解决了跨月运算的复杂性。

代码结构分为头文件声明与实现文件,测试函数TestDate1TestDate2覆盖了核心功能的验证,包括运算符逻辑、日期加减及自增行为。本文的实现兼顾效率与安全性(如const引用传参),为日期相关功能提供了可靠的底层支持。


2 概述

本文设计并实现了一个基于C++的日期类Date,支持日期的基本操作与运算。类核心功能包括:

  1. 日期合法性校验:构造函数自动检测年、月、日的有效性,对非法日期输出警告。

  2. 运算符重载:提供完整的比较运算符(==!=><等)、日期加减运算(++=--=)及自增操作(前置/后置++),使日期操作更符合直觉。

  3. 智能月份天数计算:通过私有方法GetMonthDay动态判断闰年与各月份天数,确保跨月、跨年运算的准确性。

  4. 测试验证:包含测试用例TestDate1TestDate2,验证比较逻辑、日期增减及边界条件处理的正确性。
    代码采用面向对象设计,通过封装与运算符重载提升易用性,适用于需日期处理的应用程序开发。

二、Date头文件的设计

头文件 Date.h 是整个日期类的核心声明文件,其设计遵循面向对象封装原则,通过合理划分公有接口与私有实现,确保类的安全性与易用性。以下从结构、功能与设计细节三个层面详细说明头文件的设计思路。


1. 头文件结构

头文件主要包含以下部分:

  • 预处理指令

    #pragma once  
    #include <iostream>  
    using std::cout;  
    using std::endl;  
    • #pragma once:防止头文件重复包含,保证编译安全性。

    • 仅包含必要的输入输出流头文件 <iostream>,避免冗余依赖。

    • 使用 using 声明简化 cout 和 endl 的调用,提升代码简洁性。

  • 类声明

    class Date  
    {  
    public:  // 构造函数与成员函数声明  
    private:  // 成员变量与私有方法声明  
    };  
    • 明确划分 public 与 private 区域:

      • 公有接口:暴露构造函数、打印函数及运算符重载,供外部调用。

      • 私有实现:隐藏成员变量 _year_month_day 及辅助方法 GetMonthDay,防止外部直接修改内部状态。


2. 类成员设计

(1) 成员变量

private:  int _year;  int _month;  int _day;  
  • 命名规范:采用 _ 前缀标识成员变量(如 _year),与构造函数参数 year 区分,增强可读性。

  • 数据封装:私有属性禁止外部直接访问,确保日期状态的完整性,避免非法修改。

(2) 构造函数

Date(int year = 1, int month = 1, int day = 1);  
  • 默认参数:提供默认值(1年1月1日),支持无参构造(如 Date d;)。

  • 参数校验

    • 在构造函数内部检查年、月、日的合法性:

      if (!(year >= 1 && (month >= 1 && month <= 12) && ... ))  cout << "非法日期" << endl;  
    • 确保对象初始状态有效,防止无效日期被创建。

(3) 成员函数

  • 打印函数

    void Print();  

    提供标准化的日期输出格式(如 2025/3/2),便于调试与展示。

  • 运算符重载

    // const 引用参数:提升效率并防止参数被意外修改。
    bool operator==(const Date& d);
    bool operator!=(const Date& d);
    bool operator>(const Date& d);	// d1 > d2
    bool operator>=(const Date& d); // d1 >= d2
    bool operator<=(const Date& d);
    bool operator<(const Date& d);Date& operator+=(int day);  // d1 += day
    Date operator+(int day);    // d1 + day
    Date& operator-=(int day);  // d1 -= day
    Date operator-(int day);    // d1 - day
    Date& operator++();         // 前置
    Date operator++(int);	    // 后置
    • 逻辑运算符==>等):支持日期的直接比较(如 d1 > d2)。

    • 算术运算符+=+等):实现日期的增减运算(如 d1 += 30)。

    • 参数传递:使用 const 引用(const Date& d)避免拷贝开销,同时防止参数被修改。

(4) 私有辅助方法

int GetMonthDay(int year, int month);  
  • 功能:根据年份和月份动态返回当月天数,自动处理闰年二月(29天)。

  • 实现细节

    • 静态数组 monthDayArray 存储非闰年各月天数,减少重复计算。

    • 通过闰年规则判断二月天数,提升计算效率。


3. 关键设计细节

  • 运算符复用

    • 通过复用已有运算符减少冗余代码。例如:

      bool operator!=(const Date& d) { return !(*this == d); }  
      bool operator<=(const Date& d) { return !(*this > d); }  
    • 提高代码可维护性,避免逻辑不一致。

  • 前置与后置自增

    Date& operator++();    // 前置++(返回引用)  
    Date operator++(int);  // 后置++(返回临时对象)  
    • 通过 int 参数区分前置与后置运算符,符合C++标准语法。

    • 前置自增直接修改对象并返回引用,后置自增返回旧值的副本,保证语义正确性。

  • 异常处理策略

    • 构造函数检测到非法日期时仅输出警告,未抛出异常,需由调用者确保输入的合法性。

    • 可根据需求扩展为抛出异常,增强健壮性。


4. 设计优势

  • 高内聚低耦合:日期计算逻辑封装在类内部,外部仅通过接口调用,降低依赖。

  • 语法直观性:运算符重载使日期操作符接近内置类型(如 d1 == d2),提升代码可读性。

  • 效率优化:通过引用传递、静态数组缓存天数,减少运行时开销。

该头文件的设计兼顾功能完备性与代码简洁性,为日期操作提供了高效、安全的抽象层。

三、函数实现

本节详细解析 Date 类的核心函数实现,涵盖运算符重载、日期运算逻辑及关键设计细节,确保代码功能正确性与效率优化。


1. 比较运算符重载

(1) operator== 与 operator!=

bool Date::operator==(const Date& d)
{return _year == d._year&& _month == d._month&& _day == d._day;
}
bool Date::operator!=(const Date& d)
{// 当调用 d1!=d2 时,d1 是调用该成员函数的对象,因此 this 指向 d1。// 等价于 d1.operator==(d2)return !(*this == d);
}
  • 功能:直接比较日期的年、月、日是否全等。

  • 设计亮点:通过 operator!= 复用 operator== 逻辑,避免冗余代码。

(2) operator> 与 < 系列运算符

bool Date::operator>(const Date& d)
{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;else return 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);
}
  • 关键逻辑:按年→月→日优先级逐级比较,确保判断顺序正确。


2. 日期加减运算

(1) operator+= 与 operator+

Date& Date::operator+=(int day)
{if (day < 0){return *this -= (-day);}_day += day;while (_day > GetMonthDay(_year, _month)){_day -= GetMonthDay(_year, _month);++_month;if (_month == 13){_year++;_month = 1;}}return *this;
}
Date Date::operator+(int day)
{Date& ret(*this);ret += day;return ret;
}
  • 核心算法

    • 通过循环逐月扣除天数,处理跨月、跨年场景。

    • 调用 GetMonthDay 动态获取当月天数,适配闰年规则。

(2) operator-= 与 operator-

Date& Date::operator-=(int day)
{if (day < 0){return *this += (-day);}_day -= day;while (_day <= 0){--_month;if (_month == 0){--_year;_month = 12;}_day += GetMonthDay(_year, _month);}return *this;
}Date Date::operator-(int day)
{Date& ret(*this);ret -= day;return ret;
}
  • 逆向运算逻辑:逐月回溯天数,处理跨月、跨年问题。

  • 边界处理:当 _day 减为负数时,调整月份并补足上月天数。


3. 自增运算符

(1) 前置 operator++

Date& Date::operator++()
{*this += 1;return *this;
}
  • 行为:直接修改对象,日期加1天后返回自身引用。

(2) 后置 operator++

// 后置 -- 多一个int参数主要是为了根前置区分
// 构成函数重载
Date Date::operator++(int)
{Date tmp(*this);*this += 1;return tmp;
}
  • 行为:先保存原对象状态,再自增,最后返回旧值副本。

  • 语法特性:通过 int 参数区分前置与后置运算符。


4. 辅助函数 GetMonthDay

// 函数:获取某年某月的天数
int GetMonthDay(int year, int month)
{// 定义静态变量:每月天数static int monthDayArray[13] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 };// 闰年二月有 29 天if (month == 2 && ((year % 4 == 0 && year % 100 != 0) || (year % 400 == 0))) return 29;else return monthDayArray[month];
}
  • 功能:根据年份和月份返回当月天数,自动处理闰年二月。

  • 优化设计

    • 使用静态数组缓存非闰年月份天数,减少重复初始化开销。

    • 闰年判断规则符合格里高利历标准。


5. 测试函数设计

(1) 测试逻辑运算符TestDate1

void TestDate1()
{/* 测试 ==  !=  > >= < <= */Date d1(2025, 3, 2);Date d2(d1);Date d3(2025, 3, 1);// ==  等于if (d1 == d2) cout << "==" << endl;else          cout << "!==" << endl;// !=  不等于if (d1 != d3) cout << "!=" << endl;else          cout << "!!=" << endl;// >   大于if (d1 > d3) cout << ">" << endl;else         cout << "!>" << endl;// >=  不大于等于if (d3 >= d1) cout << ">=" << endl;else         cout << "!>=" << endl;// <  小于if (d3 < d1) cout << "<" << endl;else         cout << "!<" << endl;// <  不小于等于if (d1 <= d3) cout << "<=" << endl;else         cout << "!<=" << endl;
}
  • 覆盖场景:相等日期、相邻日期、跨月边界条件。

  • 测试结果:

(2) 测试日期运算TestDate2

void TestDate2()
{/* 测试 +=  +  -=  -  前置++  后置++ */ Date d1(2025, 3, 2);Date d2(d1);Date d3(2025, 3, 1);Date d4(d3);Date d5(2025, 2, 28);// +=30   2025.4.1d1 += 30;d1.Print();// + 31   2025.4.2d2 + 31;d2.Print();// -= 31  2025.1.29d3 -= 31;d3.Print();// - 31  2025.1.29d4 - 31;d3.Print();// 1     2025.3.1d5++;d5.Print();// 1     2025.3.2++d5;d5.Print();
}
  • 关键测试点

    • 跨月运算(如 +=30 导致3月→4月)。

    • 闰年二月处理(d5++ 从2月28日到3月1日)。

    • 运算符链式调用(如 d5++ 与 ++d5 的区别)。

  • 测试结果:

四、总结与展望

 

1. 项目总结

本文设计的 Date 类通过面向对象思想与运算符重载技术,实现了日期的核心操作功能,具有以下特点:

  • 语法直观性:通过运算符重载(如 d1 += 30d1 > d2),使日期操作符的语义接近内置类型,提升代码可读性。

  • 高效性与安全性

    • 使用 const 引用传递参数,避免不必要的拷贝开销。

    • 私有方法 GetMonthDay 结合静态数组与闰年规则,高效计算月份天数。

  • 边界处理能力:支持跨月、跨年的日期运算(如从2月28日加1天到3月1日)。

  • 可扩展性:通过封装成员变量与公有接口分离,便于后续功能扩展。

测试验证

  • TestDate1 验证了比较运算符的逻辑正确性。

  • TestDate2 覆盖了日期加减、自增运算符的边界场景(如月份进位)。


2. 未来展望

为提升 Date 类的健壮性与功能性,可从以下方向优化:

功能增强

  1. 扩展日期运算

    • 实现日期差计算(如 d1 - d2 返回相差天数)。

    • 支持周数计算、星期获取(如 GetWeekDay() 返回周几)。

  2. 格式化输出

    • 支持多种日期格式(如 YYYY-MM-DDDD/MM/YYYY)。

    • 添加国际化支持(如中英文月份名称)。

性能优化

  1. 缓存优化:将 GetMonthDay 的静态数组改为全局常量,避免重复初始化。

  2. 运算符复用:通过模板或宏进一步减少比较运算符的冗余代码。

兼容性扩展

  1. 与标准库集成:兼容 std::chrono 库,支持时间戳转换与时区处理。

  2. 序列化支持:添加 Serialize() 与 Deserialize() 方法,支持日期对象的持久化存储。

测试完善

  1. 边界测试:覆盖闰年2月29日、12月31日+1天、1月1日-1天等极端场景。

  2. 模糊测试:随机生成大规模日期数据,验证运算逻辑的鲁棒性。


3. 结语

本文实现的 Date 类为C++日期操作提供了简洁高效的解决方案,其设计兼顾语法友好性与计算准确性,适用于日历应用、数据分析等场景。通过持续优化异常处理、扩展功能边界,并结合现代C++特性(如移动语义、constexpr 计算),可进一步提升其工程价值。该类的设计思想亦可为其他自定义类型的开发提供参考,体现了面向对象编程在复杂逻辑抽象中的核心优势。

五、完整代码展示

 1.Date.h

#pragma once
#include <iostream>
using std::cout;
using std::cin;
using std::endl;
class Date
{
public:// 构造函数Date(int year = 1, int month = 1, int day = 1){// _year是类的成员变量用于存储对象的状态, year为构造函数类的参数用于传递外部值到成员变量_year = year;_month = month;_day = day;// 检查日期是否合法if (!(year >= 1  // 年&& (month >= 1 && month <= 12) // 月&& (day >= 1 && day <= GetMonthDay(year, month)))) // 日{cout << "非法日期" << endl;}}void Print(){cout << _year << "/" << _month << "/" << _day << endl;}// const 引用参数:提升效率并防止参数被意外修改。bool operator==(const Date& d);bool operator!=(const Date& d);bool operator>(const Date& d);	// d1 > d2bool operator>=(const Date& d); // d1 >= d2bool operator<=(const Date& d);bool operator<(const Date& d);Date& operator+=(int day);  // d1 += dayDate operator+(int day);    // d1 + dayDate& operator-=(int day);  // d1 -= dayDate operator-(int day);    // d1 - dayDate& operator++();         // 前置Date operator++(int);	    // 后置
private:int _year;int _month;int _day;// 函数:获取某年某月的天数int GetMonthDay(int year, int month){// 定义静态变量:每月天数static int monthDayArray[13] = { 0,31,28,31,30,31,30,31,31,30,31,30,31 };// 闰年二月有 29 天if (month == 2 && ((year % 4 == 0 && year % 100 != 0) || (year % 400 == 0))) return 29;else return monthDayArray[month];}
};

2.Date.cpp

#include "Date.h"bool Date::operator==(const Date& d)
{return _year == d._year&& _month == d._month&& _day == d._day;
}
bool Date::operator!=(const Date& d)
{// 当调用 d1!=d2 时,d1 是调用该成员函数的对象,因此 this 指向 d1。// 等价于 d1.operator==(d2)return !(*this == d);
}
bool Date::operator>(const Date& d)
{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;else return 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);
}Date& Date::operator+=(int day)
{if (day < 0){return *this -= (-day);}_day += day;while (_day > GetMonthDay(_year, _month)){_day -= GetMonthDay(_year, _month);++_month;if (_month == 13){_year++;_month = 1;}}return *this;
}
Date Date::operator+(int day)
{Date& ret(*this);ret += day;return ret;
}Date& Date::operator-=(int day)
{if (day < 0){return *this += (-day);}_day -= day;while (_day <= 0){--_month;if (_month == 0){--_year;_month = 12;}_day += GetMonthDay(_year, _month);}return *this;
}Date Date::operator-(int day)
{Date& ret(*this);ret -= day;return ret;
}Date& Date::operator++()
{*this += 1;return *this;
}// 后置 -- 多一个int参数主要是为了根前置区分
// 构成函数重载
Date Date::operator++(int)
{Date tmp(*this);*this += 1;return tmp;
}

3. Test.cpp

#include "Date.h"void TestDate1()
{/* 测试 ==  !=  > >= < <= */Date d1(2025, 3, 2);Date d2(d1);Date d3(2025, 3, 1);// ==  等于if (d1 == d2) cout << "==" << endl;else          cout << "!==" << endl;// !=  不等于if (d1 != d3) cout << "!=" << endl;else          cout << "!!=" << endl;// >   大于if (d1 > d3) cout << ">" << endl;else         cout << "!>" << endl;// >=  不大于等于if (d3 >= d1) cout << ">=" << endl;else         cout << "!>=" << endl;// <  小于if (d3 < d1) cout << "<" << endl;else         cout << "!<" << endl;// <  不小于等于if (d1 <= d3) cout << "<=" << endl;else         cout << "!<=" << endl;
}
void TestDate2()
{/* 测试 +=  +  -=  -  前置++  后置++ */ Date d1(2025, 3, 2);Date d2(d1);Date d3(2025, 3, 1);Date d4(d3);Date d5(2025, 2, 28);// +=30   2025.4.1d1 += 30;d1.Print();// + 31   2025.4.2d2 + 31;d2.Print();// -= 31  2025.1.29d3 -= 31;d3.Print();// - 31  2025.1.29d4 - 31;d3.Print();// 1     2025.3.1d5++;d5.Print();// 1     2025.3.2++d5;d5.Print();
}int main()
{//TestDate1();TestDate2();return 0;
}

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

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

相关文章

【网络安全】——协议逆向与频繁序列提取:从流量中解码未知协议

目录 引言 一、为什么要结合频繁序列提取&#xff1f; 二、四步融合分析法 步骤1&#xff1a;原始流量采集与预处理 步骤2&#xff1a;多粒度序列模式挖掘 层1&#xff1a;单包内字节级频繁项 层2&#xff1a;跨数据包的行为序列 步骤3&#xff1a;关键字段定位与结构假…

【PAT (Basic Level) Practice】——【数论】1013 数素数

文章目录 一【题目难度】二【题目编号】三【题目描述】四【题目示例】五【解题思路】六【最终得分】七【代码实现】八【提交结果】 一【题目难度】 乙级 二【题目编号】 1013 数素数 三【题目描述】 令 Pi 表示第 i 个素数。现任给两个正整数 M≤N≤104&#xff0c;请输出…

HCIA—IP路由静态

一、概念及作用 1、概念&#xff1a;IP路由是指在IP网络中&#xff0c;数据从源节点到目的节点所经过的路径选择和数据转发的过程。 2、作用 ①实现网络互联&#xff1a;使不同网段的设备能够相互通信&#xff0c;构建大规模的互联网络 ②优化网络拓扑&#xff1a;根据网络…

雷池WAF的为什么选择基于Docker

Docker 是一种开源的容器化平台&#xff0c;可以帮助开发人员将应用程序及其所有依赖项打包到一个称为容器的独立、可移植的环境中。Docker 的核心概念包括以下几点&#xff1a; 容器&#xff1a;Docker 使用容器来封装应用程序及其依赖项&#xff0c;使其能够在任何环境中都能…

图像分类项目2:鸟类图像分类

1 数据集处理 1.1数据集下载 数据集来源&#xff1a;kaggle&#xff0c;网址&#xff1a;https://www.kaggle.com/&#xff0c;点击进入网站&#xff0c;左侧选择Datasets。 进入后搜索栏搜索关键词bird。此时出现很多数据集可以选择&#xff0c;推荐选择第一个或者第三个。…

01_NLP基础之文本处理的基本方法

自然语言处理入门 自然语言处理&#xff08;Natural Language Processing, 简称NLP&#xff09;是计算机科学与语言学中关注于计算机与人类语言间转换的领域&#xff0c;主要目标是让机器能够理解和生成自然语言&#xff0c;这样人们可以通过语言与计算机进行更自然的互动。 …

利用opencv_python(pdf2image、poppler)将pdf每页转为图片

1、安装依赖pdf2image pip install pdf2image 运行.py报错&#xff0c;因为缺少了poppler支持。 2、安装pdf2image的依赖poppler 以上命令直接报错。 改为手工下载&#xff1a; github: Releases oschwartz10612/poppler-windows GitHub 百度网盘&#xff1a; 百度网盘…

IDEA入门及常用快捷键

IDEA是java常用的IDE。当run一个.java文件时&#xff0c;其实是经历了先编译为.class&#xff0c;再运行的过程。 在project文件夹中&#xff0c;out文件夹存储编译的.class文件&#xff0c;src文件夹存储.java代码文件。 设置自动导包 快捷键&#xff1a; 格式化快捷键&…

io学习----->文件io

思维导图&#xff1a; 一.文件io的概念 文件IO&#xff1a;指程序和文件系统之间的数据交互 特点&#xff1a; 1.不存在缓冲区&#xff0c;访问速度慢 2.不可以移植&#xff0c;依赖于操作系统 3.可以访问不同的文件类型(软连接&#xff0c;块设备等) 4.文件IO属于系统调…

深入探索WebGL:解锁网页3D图形的无限可能

深入探索WebGL&#xff1a;解锁网页3D图形的无限可能 引言 。WebGL&#xff0c;作为这一变革中的重要技术&#xff0c;正以其强大的功能和广泛的应用前景&#xff0c;吸引着越来越多的开发者和设计师的关注。本文将深入剖析WebGL的核心原理、关键技术、实践应用&#xff0c;并…

从开发和对抗的角度思考web网页中的接口逆向

如何从开发和对抗的角度去思考web网页中的接口逆向。 文章目录 前言1.从开发和对抗的角度思考接口逆向1.1 什么是接口逆向1.2 开发的角度思考如何开发策略1.3 对抗的角度思考遇到的问题1.4 正常情况下开发者如何防护1.5 正常情况攻击者如何做&#xff1f;1.6 对抗中的胜者 2.某…

C++24--右值引用C++11新特性

目录 1.C11简介 2.统一的列表初始化 2.1{}初始化 2.2std::initializer_list 3.声明 3.1auto 3.2decltype 3.3nullptr 4.范围for循环 5.智能指针 6.右值引用和移动语义 6.1左值引用和右值引用 6.2左值引用与右值引用比较 6.3右值引用使用场景和意义 6.4右值引用引…

Android ChatOn-v1.66.536-598-[构建于ChatGPT和GPT-4o之上]

ChatOn 链接&#xff1a;https://pan.xunlei.com/s/VOKYnq-i3C83CK-HJ1gfLf4gA1?pwdwzwc# 添加了最大无限积分 删除了所有调试信息 语言&#xff1a;全语言支持

Java高频面试之集合-03

hello啊&#xff0c;各位观众姥爷们&#xff01;&#xff01;&#xff01;本baby今天来报道了&#xff01;哈哈哈哈哈嗝&#x1f436; 面试官&#xff1a;说说ArrayList和LinkedList的区别 ArrayList 与 LinkedList 的详细对比 一、底层数据结构 特性ArrayListLinkedList存…

华为hcie证书有什么作用?

新盟教育 专注华为认证培训十余年 为你提供认证一线资讯&#xff01; 在当今数字化飞速发展的时代&#xff0c;ICT行业对专业人才的需求日益增长。华为HCIE证书作为华为认证体系中的最高级别认证&#xff0c;无疑是众多IT从业者追求的目标。那么&#xff0c;华为HCIE证书到底有…

通过微步API接口对单个IP进行查询

import requests import json# 微步API的URL和你的API密钥 API_URL "https://api.threatbook.cn/v3/ip/query" API_KEY "***" # 替换为你的微步API密钥 def query_threatbook(ip):"""查询微步API接口&#xff0c;判断IP是否为可疑"…

Redis|集群 Cluster

文章目录 是什么能干嘛集群算法-分片-槽位slotredis集群的槽位slotredis集群的分片分片槽位的优势slot槽位映射——业界的3种解决方案小厂&#xff1a;哈希取余分区中厂&#xff1a;一致性哈希算法分区大厂&#xff1a;哈希槽分区 面试题&#xff1a;为什么 Redis 集群的最大槽…

城市地质安全专题连载⑧ | 强化工程地质安全保障力度,为工程项目全栈护航

作者 | 徐海洋、孙美琴 在城市化进程日益加速的今天&#xff0c;城市地质安全问题日益凸显&#xff0c;成为制约城市可持续发展的关键因素之一。从隧道掘进中的突发灾害&#xff0c;到高层建筑地基的稳定性挑战&#xff0c;再到城市地下空间的开发利用风险&#xff0c;地质安全…

工厂模式:简单工厂、工厂方法以及抽象工厂

文章目录 前言简单工厂模式优缺点 工厂方法模式优缺点 抽象工厂优缺点 前言 工厂模式是一种创建型设计模式&#xff0c;其作用是将对象的创建和使用进行解耦&#xff0c;用于提高代码的可维护性和可扩展性。通过提供给外部负责创建对象的工厂类&#xff0c;外部类通过工厂来创…

FFMPEG利用H264+AAC合成TS文件

本次的DEMO是利用FFMPEG框架把H264文件和AAC文件合并成一个TS文件。这个DEMO很重要&#xff0c;因为在后面的推流项目中用到了这方面的技术。所以&#xff0c;大家最好把这个项目好好了解。 下面这个是流程图 从这个图我们能看出来&#xff0c;在main函数中我们主要做了这几步&…