开源 - Ideal库 -获取特殊时间扩展方法(四)

news/2024/11/14 0:15:32/文章来源:https://www.cnblogs.com/hugogoos/p/18539591

书接上回,我们继续来分享一些关于特殊时间获取的常用扩展方法。

01、获取当前日期所在月的第一个指定星期几

该方法和前面介绍的获取当前日期所在周的第一天(周一)核心思想是一样的,只是把求周一改成求周几而已,当然其中有些小细节需要注意,比如求所在周的第一天则两天都在同一周,而求所在月第一个指定周则可能两天在不同周,具体代码如下:

//获取当前日期所在月的第一个指定星期几
public static DateTime GetFirstDayOfWeekDateTimeInMonth(this DateTime dateTime, DayOfWeek dayOfWeek)
{//获取当前日期所在月的第一天var firstDayOfMonth = dateTime.GetFirstDayDateTimeOfMonth();//计算目标日期与当月第一天相差天数var diff = ((int)dayOfWeek - (int)firstDayOfMonth.DayOfWeek + 7) % 7;return firstDayOfMonth.AddDays(diff);
}

下面我们还需要做详细的单元测试,我们分别测试指定周一和周日两个特殊日期,然后再分别测试三种特殊情况:

指定周一测试:

(1) 验证当前日期是周五,而周一在下一周的情况;

(2) 验证当前日期是本月第一个周一的情况;

(3) 验证当前日期是周日,并且在本月第一个周一之后的情况;

指定周日测试:

(1) 验证当前日期是周五,并且在本月第一个周日之前的情况;

(2) 验证当前日期是本月第一个周日的情况;

(3) 验证当前日期是周一,并且在本月第一个周日之后的情况;

具体代码如下:

[Fact]
public void GetFirstDayOfWeekDateTimeInMonth()
{//验证当前日期是周五,而周一在下一周的情况var friday_monday = new DateTime(2024, 11, 1, 14, 10, 10);var day_friday_monday = friday_monday.GetFirstDayOfWeekDateTimeInMonth(DayOfWeek.Monday);Assert.Equal(new DateTime(2024, 11, 4), day_friday_monday);//验证当前日期是本月第一个周一的情况var monday_monday = new DateTime(2024, 11, 4, 4, 10, 10);var day_monday_monday = monday_monday.GetFirstDayOfWeekDateTimeInMonth(DayOfWeek.Monday);Assert.Equal(new DateTime(2024, 11, 4), day_monday_monday);//验证当前日期是周日,并且在本月第一个周一之后的情况var sunday_monday = new DateTime(2024, 11, 30, 4, 10, 10);var day_sunday_monday = sunday_monday.GetFirstDayOfWeekDateTimeInMonth(DayOfWeek.Monday);Assert.Equal(new DateTime(2024, 11, 4), day_sunday_monday);//验证当前日期是周五,并且在本月第一个周日之前的情况var friday_sunday = new DateTime(2024, 11, 1, 14, 10, 10);var day_friday_sunday = friday_sunday.GetFirstDayOfWeekDateTimeInMonth(DayOfWeek.Sunday);Assert.Equal(new DateTime(2024, 11, 3), day_friday_sunday);//验证当前日期是本月第一个周日的情况var sunday_sunday = new DateTime(2024, 11, 30, 4, 10, 10);var day_sunday_sunday = sunday_sunday.GetFirstDayOfWeekDateTimeInMonth(DayOfWeek.Sunday);Assert.Equal(new DateTime(2024, 11, 3), day_sunday_sunday);//验证当前日期是周一,并且在本月第一个周日之后的情况var monday_sunday = new DateTime(2024, 11, 4, 4, 10, 10);var day_monday_sunday = monday_sunday.GetFirstDayOfWeekDateTimeInMonth(DayOfWeek.Sunday);Assert.Equal(new DateTime(2024, 11, 3), day_monday_sunday);
}

02、获取当前日期所在月的最后一个指定星期几

该方法和上一个求第一个指定星期几核心思想是一样的,具体代码如下:

//获取当前日期所在月的最后一个指定星期几
public static DateTime GetLastDayOfWeekDateTimeInMonth(this DateTime dateTime, DayOfWeek dayOfWeek)
{//获取当前日期所在月的最后一天var lastDayOfMonth = dateTime.GetLastDayDateTimeOfMonth();//计算目标日期与当月最后一天相差天数var diff = ((int)lastDayOfMonth.DayOfWeek - (int)dayOfWeek + 7) % 7;return lastDayOfMonth.AddDays(-diff);
}

单元测试可以参考求第一个指定星期几,这里就不赘述了。

03、获取当前日期上一个指定星期几

求上一个指定周几,其实也不复杂,首先计算出当前日期与目标星期几相差的天数,其中有个小细节需要注意,就是如果两个日期相同,则需要把相差天数改为7,具体代码如下:

//获取当前日期上一个指定星期几
public static DateTime GetPreviousDayDateTimeOfWeek(this DateTime dateTime, DayOfWeek dayOfWeek)
{//计算当前日期与目标星期几相差天数var diff = ((int)dateTime.DayOfWeek - (int)dayOfWeek + 7) % 7;//如果相差0天表示当前日期和目标星期几相同,需要改为7diff = diff == 0 ? 7 : diff;return dateTime.AddDays(-diff).Date;
}

我们分别对以下四种情况做单元测试:

(1) 验证当前日期是周一,而上一个周一在上一月的情况;

(2) 验证当前日期是周一,而上一个周一在当月的情况;

(3) 验证当前日期是周日,而上一个周一在当月的情况;

(4) 验证当前日期是周六,并且是当月最后一天的情况;

具体代码如下:

[Fact]
public void GetPreviousDayDateTimeOfWeek()
{//验证当前日期是周一,而上一个周一在上一月的情况var monday = new DateTime(2024, 11, 1, 14, 10, 10);var day_monday = monday.GetPreviousDayDateTimeOfWeek(DayOfWeek.Monday);Assert.Equal(new DateTime(2024, 10, 28), day_monday);//验证当前日期是周一,而上一个周一在当月的情况var monday1 = new DateTime(2024, 11, 25, 14, 10, 10);var day_monday1 = monday1.GetPreviousDayDateTimeOfWeek(DayOfWeek.Monday);Assert.Equal(new DateTime(2024, 11, 18), day_monday1);//验证当前日期是周日,而上一个周一在当月的情况var sunday = new DateTime(2024, 11, 24, 4, 10, 10);var day_sunday = sunday.GetPreviousDayDateTimeOfWeek(DayOfWeek.Monday);Assert.Equal(new DateTime(2024, 11, 18), day_sunday);//验证当前日期是周六,并且是当月最后一天的情况var saturday = new DateTime(2024, 11, 30, 4, 10, 10);var day_saturday = saturday.GetPreviousDayDateTimeOfWeek(DayOfWeek.Monday);Assert.Equal(new DateTime(2024, 11, 25), day_saturday);
}

04、获取当前日期下一个指定星期几

该方法和上面获取上一个指定星期几核心思想相同,具体代码如下:

//获取当前日期下一个最近指定星期几
public static DateTime GetNextDayDateTimeOfWeek(this DateTime dateTime, DayOfWeek dayOfWeek)
{//计算目标日期与当月最后一天相差天数var diff = ((int)dayOfWeek - (int)dateTime.DayOfWeek + 7) % 7;//如果相差0天表示当前日期和目标星期几相同,需要改为7diff = diff == 0 ? 7 : diff;return dateTime.AddDays(diff).Date;
}

单元测试也可以参考求上一个指定星期几,这里就不再赘述了。

05、获取当前日期是其所在月的第几周

该方法的核心思想是,获取当前日期和当月第一天相差多少天,然后用相差的天数除以7即可获得当前是第几周。

但是这里有个比较麻烦的事情是如果第一周不满一周呢,比如当月的第一周第一天是2024-11-01周五,而今天是2024-11-07周四,应该是当月的第二周,但是如果直接计算两天的差再除以7结果显然是不对的。

因此我们首先需要把第一周不满一周的天数补上,即前面还有4天。

如此就是(7+4)/7=1…4,即所在第二周,其中商表示完整的周,余数则表示不完整的周。如果转为公式则为:days/7 + (days%7 > 0 ? 1 : 0),我们对这个公式简化后得到:(days + 6)/7,具体实现代码如下:

//获取当前日期是其所在月的第几周
public static int GetWeekOfMonth(this DateTime dateTime)
{//获取当前日期所在月的第一天var firstDayOfMonth = dateTime.GetFirstDayDateTimeOfMonth();//首先设定周一为一周的开始//计算当前月第一天与周一相差天数//即第一周如果不满一周还差多少天var diff = ((int)firstDayOfMonth.DayOfWeek - (int)DayOfWeek.Monday + 7) % 7;//用第一周不满的差值加上当前日期的天数之和计算当前为当月第几周//然后计算 总天数/7的商,如果有余数则再加1//公式为:n/7 + (n%7 > 0 ? 1 : 0)//上面公式可以简化为 (n+6)/7return (diff + dateTime.Day + 6) / 7;
}

下面我们对其进行以下几种情况详细的单元测试:

(1) 验证当前日期是周五,且是当月第一天的情况;

(2) 验证当前日期是周日,且在当月第一周的情况;

(3) 验证当前日期是周一,且在当月第三周的情况;

(4) 验证当前日期是周日,且在当月第三周的情况;

(5) 验证当前日期是周六,且是当月最后一天的情况;

具体代码如下:

[Fact]
public void GetWeekOfMonth()
{//验证当前日期是周五,且是当月第一天的情况var friday = new DateTime(2024, 11, 1, 14, 10, 10);var day_friday = friday.GetWeekOfMonth();Assert.Equal(1, day_friday);//验证当前日期是周日,且在当月第一周的情况var sunday = new DateTime(2024, 11, 3, 14, 10, 10);var day_sunday = sunday.GetWeekOfMonth();Assert.Equal(1, day_sunday);//验证当前日期是周一,且在当月第三周的情况var monday = new DateTime(2024, 11, 11, 4, 10, 10);var day_monday = monday.GetWeekOfMonth();Assert.Equal(3, day_monday);//验证当前日期是周日,且在当月第三周的情况var date17 = new DateTime(2024, 11, 17, 4, 10, 10);var day17 = date17.GetWeekOfMonth();Assert.Equal(3, day17);//验证当前日期是周六,且是当月最后一天的情况var sunday1 = new DateTime(2024, 11, 30, 4, 10, 10);var day_sunday1 = sunday1.GetWeekOfMonth();Assert.Equal(5, day_sunday1);
}

06、获取当前日期是其所在年的第几周(ISO 8601 标准)

在ISO 8601 标准规定中,每周从星期一开始,且每年最少有 52 周,每年的第一周是包含该年第一天的那一周,且该周必须至少有四天。

获取当然日期所在年的第几周可以通过调用C#中文化信息中日历组件中GetWeekOfYear方法,具体代码如下:

//获取当前日期是其所在年的第几周(ISO 8601 标准)
public static int GetWeekOfYear(this DateTime dateTime)
{var currentCulture = CultureInfo.CurrentCulture;return currentCulture.Calendar.GetWeekOfYear(dateTime, currentCulture.DateTimeFormat.CalendarWeekRule, currentCulture.DateTimeFormat.FirstDayOfWeek);
}

07、获取当前日期所在月份的周数

该方法实现的核心思想是首先获取当前日期所在月份的第一天和最后一天,然后分别计算其所在当年第几周,最后相减即可得到,具体代码如下:

//获取当前日期所在月份的周数
public static int GetWeeksInMonth(this DateTime dateTime)
{//获取当前日期所在月的第一天var firstDayOfMonth = dateTime.GetFirstDayDateTimeOfMonth();//获取当前日期所在月的最后一天var lastDayOfMonth = dateTime.GetLastDayDateTimeOfMonth();//获取当月第一天在全年中的周数var firstWeek = firstDayOfMonth.GetWeekOfYear();//获取当月最后一天在全年中的周数var lastWeek = lastDayOfMonth.GetWeekOfYear();return lastWeek - firstWeek + 1;
}

08、判断当前日期是否是周末

该方法比较简单,只是判断当前是否是否为周六或周日,具体代码如下:

//判断当前日期是否是周末
public static bool IsWeekend(this DateTime dateTime)
{return dateTime.DayOfWeek == DayOfWeek.Saturday || dateTime.DayOfWeek == DayOfWeek.Sunday;
}

09、判断当前日期所在年是否是闰年

该方法调用了C#内置方法IsLeapYear,具体代码如下:

//判断当前日期所在年是否是闰年
public static bool IsLeapYear(this DateTime dateTime)
{return DateTime.IsLeapYear(dateTime.Year);
}

10、获取当前日期所在季度

该方法也比较简单,只需要应用一个小公式即可求的,具体代码如下:

//获取当前日期所在季度
public static int GetQuarter(this DateTime dateTime)
{return (dateTime.Month - 1) / 3 + 1;
}

稍晚些时候我会把库上传至Nuget,大家可以直接使用Ideal.Core.Common。

:测试方法代码以及示例源码都已经上传至代码库,有兴趣的可以看看。https://gitee.com/hugogoos/Ideal

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

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

相关文章

关于Windows外壳(Windows Shell)

在前面的文章中,我介绍过如何替换Windows Shell,将桌面替换为自己的程序。 但是这么做会有个问题,就是桌面环境未被初始化,即使创建了explorer.exe进程,桌面也不会出现。 这里搜集了一些关于WInlogon,LogonUI和Userinit的一些理论知识,有兴趣的小伙伴可以了解一下。Winlo…

如何修复 iPhone 无法通过 Quik App 的蓝牙连接来启动 GoPro Hero13 Black 的解决方案 All In One

如何修复 iPhone 无法通过 Quik App 的蓝牙连接来启动 GoPro Hero13 Black 的解决方案 All In One 最近再使用 GoPro Hero13 Black 的过程中发现 iPhone 经常无法通过 Quik App 的蓝牙唤起 GoPro 开机,需要手动删除 iPhone 的蓝牙匹配,并重新配对 GoPro, 非常麻烦和使用体验极…

VUE使用TS开发打包时发现校验问题无法打包

解决办法: 找到 tsconfig.app.json 这个文件,把他的include改为一个实际存在的空文件即可

企业博客在品牌建设中的作用

在数字营销时代,企业博客已成为品牌建设的重要工具。它不仅帮助企业与目标受众建立联系,还能够提升品牌形象、增强客户忠诚度,并推动销售。本文将探讨企业博客在品牌建设中的关键作用,并结合实际案例分析其效果。 一、建立品牌权威性 企业博客是展示行业知识和专业能力的平…

2024ICPC杭州赛后总结

首先,还是恭喜一下我们队第一次参赛就拿到了,非常的幸运赛前事情还得从网络赛说起,由于我们队网络赛的发挥实在不好,导致最后只得到了一场比赛机会,在选择赛站的时候,就非常的犹豫,我们知道等学长都选完之后,留下给我们的赛站就不多了,我们应该选一个比较有举办经验的…

vm安装ubuntu 20.04 server并用vscode进行ssh远程连接

最近写专业课作业需要用到vscode进行SSH连接ubuntu server,自己摸索了一会终于实现效果,秉承着“取之于网络,还之于网络”的开源精神写了一篇总结博客,欢迎大家参考,如有不足之处也欢迎大家指出。 文章参考: VS Code SSH远程连接Ubuntu_visual studio 连接到本地unbuntu远…

项目冲刺11.11

这个作业属于哪个课程 计科22级34班这个作业要求在哪里 作业要求这个作业的目标 进行为期七天的项目冲刺并记录前言 本篇博客是项目冲刺的第一篇,七篇博客的汇总如下:博客汇总第一篇博客第二篇博客第三篇博客第四篇博客第五篇博客第六篇博客第七篇博客团队简介队名 拖延是你不…

P1625求和 题解

P1625 求和 题解 题意 求和 题解 比较好想,小学一年级奥数可以理解为高精度的大杂烩 代码很简洁,可自行理解 #include<bits/stdc++.h> //万能头 #define ll long long // 开long long using namespace std;// 命名空间 ll n,m,a[2005],b[2005],c[4000005]; //a[0]…

Power Automate 导出CSV文件中文乱码

前言最近有酱紫一个需求,就是用户想要使用Power Automate导出CSV文件,其实本身操作是灰常简单的,但是,出现了中文乱码的情况。正文1.不过没关系了,不服就干!我们在发送邮件的CSV内容里,简单的处理下就可以了,如下图:   2.处理的方式,如下:concat(uriComponentToSt…

reverse3

题目链接:reverse3。 下载附件后,使用 IDA 打开,进行反编译,定位到 main 函数如下。通过分析 main 函数流程,可以发现主要是对用户输入的字符串进行了两次操作,第一次是函数 "sub_4110BE",第二次是对函数 "sub_4110BE" 处理后得到的字符串进行简单的…

Linux基础日志分析

四、日志分析 【1】、what is 日志日志log 分析,检查系统,服务是否正常运行,一般都要看日志。 后面学习的一些服务软件,遇到故障就要查看日志。 Linux日志一般存放在/var/log/目录。【2】、核心日志ip,root,密码,22(端口)Linux默认核心日志 说明/var/log/secure(麒麟,红…