给定一个 NSDate,找到前第四个月的最后一天
Given an NSDate, find the last day of fourth prior month
我正在尝试根据当前日期计算 NSDate 对象。如果当前日期是 2015 年 4 月 1 日,我需要生成日期 2014 年 12 月 31 日。如果当前日期是 2015 年 4 月 30 日,我仍然需要生成日期 2014 年 12 月 31 日。但是,如果是2015 年 5 月 1 日,我需要生成 2015 年 1 月 31 日。换句话说,无论我在哪个月份,我都需要四个月前的月末日期,无论我在当前月份的哪个位置。
我目前的代码是:
NSCalendar *theCalendar = [NSCalendar currentCalendar];
NSDateComponents *dayComponent = [[NSDateComponents alloc] init];
[dayComponent setDay:-90];
NSDate *nextDate = [theCalendar dateByAddingComponents:dayComponent toDate:[NSDate date] options:0];
NSLog(@"The date I am getting is: %@", nextDate);
上面的代码给出了当前日期前 90 天的日期值,但我需要日期始终是 4 个月前的月末。
您想熟悉 NSCalendar
和 NSDateComponents
。如果您阅读了那两个 API 文档,您将能够 assemble 找到答案。
从概念上讲,您想使用 NSCalendar
components:fromDate:
来获取当前日期的组成部分(日、月、年)。
然后您会将那个月的值倒退 4 个月。现在,如果过了 1 月,您就知道需要确定多少,以便调整并保持在几个月内 [1..12]。此外,您还需要在那时减少年份。
知道月份,可以通过多种方式找到该月的最后一天;最粗略的方法是维护您自己的枚举...但是使用 NSCalendar 可能有更好的方法,它也将计算闰年的二月。
最后,您可以使用 NSCalendar
方法 dateFromComponents:
.
从您 assembled 的组件构建结果日期
请参阅@rob mayoff 的出色答案,这是对该理论和 IMO 的更具体实现,正确答案。
正如您已经发现的那样,您需要一个开始日期和一个日历:
NSDate *startingDate = [NSDate date];
NSCalendar *calendar = [NSCalendar autoupdatingCurrentCalendar];
您将需要当前日期的组成部分,但只需要到当前月份,因为您不关心该月中的具体日期:
NSDateComponents *components = [calendar
components:NSCalendarUnitEra | NSCalendarUnitYear | NSCalendarUnitMonth
fromDate:startingDate];
你说你想要前一个月的最后一天。由于月份的天数不同,因此最后一天因月份而异。但是所有月份都有第一天,而第一天总是编号为 1。因此,通过先回溯三个月来计算“前第四个月的最后一天”最简单:
components.month -= 3;
然后,去那个月的前一天:
components.day = -1;
最后,你需要在头脑中弄清楚 NSDate
代表时间上的 瞬间 ,而是一天(比如“2015 年 4 月 1 日”)是一个 间隔 的时间,在特定时刻开始和结束。如果您要使用 NSDate
表示一整天,您将在该时间间隔内存储一个瞬间。您不想 存储第一个或最后一个瞬间(它们都是午夜); that causes problems for some days in some time zones。相反,使用中午作为即时:
components.hour = 12;
现在您可以向日历请求新的 NSDate
:
NSDate *lastDayOfFourthPriorMonth = [calendar dateFromComponents:components];
我正在尝试根据当前日期计算 NSDate 对象。如果当前日期是 2015 年 4 月 1 日,我需要生成日期 2014 年 12 月 31 日。如果当前日期是 2015 年 4 月 30 日,我仍然需要生成日期 2014 年 12 月 31 日。但是,如果是2015 年 5 月 1 日,我需要生成 2015 年 1 月 31 日。换句话说,无论我在哪个月份,我都需要四个月前的月末日期,无论我在当前月份的哪个位置。
我目前的代码是:
NSCalendar *theCalendar = [NSCalendar currentCalendar];
NSDateComponents *dayComponent = [[NSDateComponents alloc] init];
[dayComponent setDay:-90];
NSDate *nextDate = [theCalendar dateByAddingComponents:dayComponent toDate:[NSDate date] options:0];
NSLog(@"The date I am getting is: %@", nextDate);
上面的代码给出了当前日期前 90 天的日期值,但我需要日期始终是 4 个月前的月末。
您想熟悉 NSCalendar
和 NSDateComponents
。如果您阅读了那两个 API 文档,您将能够 assemble 找到答案。
从概念上讲,您想使用 NSCalendar
components:fromDate:
来获取当前日期的组成部分(日、月、年)。
然后您会将那个月的值倒退 4 个月。现在,如果过了 1 月,您就知道需要确定多少,以便调整并保持在几个月内 [1..12]。此外,您还需要在那时减少年份。
知道月份,可以通过多种方式找到该月的最后一天;最粗略的方法是维护您自己的枚举...但是使用 NSCalendar 可能有更好的方法,它也将计算闰年的二月。
最后,您可以使用 NSCalendar
方法 dateFromComponents:
.
请参阅@rob mayoff 的出色答案,这是对该理论和 IMO 的更具体实现,正确答案。
正如您已经发现的那样,您需要一个开始日期和一个日历:
NSDate *startingDate = [NSDate date];
NSCalendar *calendar = [NSCalendar autoupdatingCurrentCalendar];
您将需要当前日期的组成部分,但只需要到当前月份,因为您不关心该月中的具体日期:
NSDateComponents *components = [calendar
components:NSCalendarUnitEra | NSCalendarUnitYear | NSCalendarUnitMonth
fromDate:startingDate];
你说你想要前一个月的最后一天。由于月份的天数不同,因此最后一天因月份而异。但是所有月份都有第一天,而第一天总是编号为 1。因此,通过先回溯三个月来计算“前第四个月的最后一天”最简单:
components.month -= 3;
然后,去那个月的前一天:
components.day = -1;
最后,你需要在头脑中弄清楚 NSDate
代表时间上的 瞬间 ,而是一天(比如“2015 年 4 月 1 日”)是一个 间隔 的时间,在特定时刻开始和结束。如果您要使用 NSDate
表示一整天,您将在该时间间隔内存储一个瞬间。您不想 存储第一个或最后一个瞬间(它们都是午夜); that causes problems for some days in some time zones。相反,使用中午作为即时:
components.hour = 12;
现在您可以向日历请求新的 NSDate
:
NSDate *lastDayOfFourthPriorMonth = [calendar dateFromComponents:components];