Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

【iOS】DateTools使用「日期工具库」 #22

Open
ShowJoy-com opened this issue Mar 6, 2017 · 0 comments
Open

【iOS】DateTools使用「日期工具库」 #22

ShowJoy-com opened this issue Mar 6, 2017 · 0 comments

Comments

@ShowJoy-com
Copy link
Owner

ShowJoy-com commented Mar 6, 2017

本文来自尚妆iOS团队嘉文
发表于尚妆github博客,欢迎订阅!

准备:

DateTools_下载

DateTools

DateTools是Objective-C中简化日期和时间处理的工具.

安装


CocoaPods
pod 'DateTools'

手动安装
DataTools所需的所有类包含在DataTools文件夹下,如下:

  • DateTools.h
  • NSDate+DateTools.{h,m}
  • DTConstants.h
  • DTError.{h,m}
  • DTTimePeriod.{h,m}
  • DTTimePeriodGroup.{h,m}
  • DTTimePeriodCollection.{h,m}
  • DTTimePeriodChain.{h,m}

如果你的工程想要支持国际化或者使用"TimeAgo"功能必须要导入bundle文件
你可以在工程中Info下添加Localizations来添加支持的语言

  • DateTools.bundle

 

DateTools.h 包含了所有其他文件的头文件.在你的工程中导入DateTools.h头文件即可

DateTools中包含3个子库

  • NSDate+DateTools
  • Time Periods
  • Time Period Groups

基本使用

NSDate+DateTools


1.Time Ago(相对日期形式)

Time ago 就是将日期转变为相对日期的形式,即我们常用的“昨天、今天、明天、几天前,一周以后……”这样的表述方式。

NSDate *timeAgoDate = [NSDate dateWithTimeIntervalSinceNow:-4];
NSLog(@"Time Ago: %@", timeAgoDate.timeAgoSinceNow);
NSLog(@"Time Ago: %@", timeAgoDate.shortTimeAgoSinceNow);

//输出:
//Time Ago: 4 seconds ago 
//Time Ago: 4s 

//设置好支持中文输出:
//Time Ago: 4秒钟前 
//Time Ago: 4秒

DateTools提供了多达33种语言的支持
如果想修改相对日期显示的文字,可以修改DateTools/Resources/DateTools.bundle下相应的文件
下图以简体中文为例:

修改相对日期显示文字

2.Date Components(日期组成部分)

获取日期的组成部分:

NSDate *date = [NSDate date];
NSInteger year = date.year;
NSInteger month = date.month;
NSInteger day = date.day;
NSInteger hour = date.hour;
NSInteger minute = date.minute;
NSInteger second = date.second;
    
NSLog(@"year:%ld month:%ld day:%ld hour:%ld minute:%ld second:%ld", year, month, day, hour, minute, second);
//输出: year:2016 month:5 day:23 hour:10 minute:54 second:1

DateTools默认日历为公历!!!
使用其他日历:
(如果想全局使用其他日历,修改DateTools默认日历,可以改写 NSDate+DateTools.m 中的 defaultCalendar 方法)

日历枚举

/**
  *  使用中国农历
  */
NSCalendar *calendar = [[NSCalendar alloc] initWithCalendarIdentifier:NSChineseCalendar];
    
NSDate *date = [NSDate date];
NSInteger year = [date yearWithCalendar:calendar];
NSInteger month = [date monthWithCalendar:calendar];
NSInteger day = [date dayWithCalendar:calendar];
NSInteger hour = [date hourWithCalendar:calendar];
NSInteger minute = [date minuteWithCalendar:calendar];
NSInteger second = [date secondWithCalendar:calendar];
    
NSLog(@"农历: %ld-%ld-%ld %ld:%ld:%ld", year, month, day, hour, minute, second);
NSLog(@"公历: %ld-%ld-%ld %ld:%ld:%ld", date.year, date.month, date.day, date.hour, date.minute, date.second);
//输出: 农历: 33-4-17 11:41:51
//输出: 公历: 2016-5-23 11:41:51

3.日期编辑

对日期进行编辑(年,月,日,星期,时,分,秒)
增加/减少方法:

日期编辑

/**
  *  日期增加1年
  */
NSDate *date = [NSDate date];
NSDate *newDate = [date dateByAddingYears:1];
 
NSLog(@"year:%ld newYear:%ld", date.year, newDate.year);
//输出: year:2016 newYear:2017

4.日期比较

比较两个日期大小返回一个布尔值:

日期比较

更多日期比较方法:
(很容易的得到两个日期相差的年,月,星期,日,时,分,秒)

更多日期比较方法

5.格式化日期字符串

formattedDateWithStyle:(系统格式)
formattedDateWithFormat:(自定义格式)

格式化日期字符串

/**
  *  formattedDateWithStyle(系统格式)
  */
NSDate *date = [NSDate date];
NSString *dateStringNo = [date formattedDateWithStyle:NSDateFormatterNoStyle];
NSString *dateStringShort = [date formattedDateWithStyle:NSDateFormatterShortStyle];
NSString *dateStringMedium = [date formattedDateWithStyle:NSDateFormatterMediumStyle];
NSString *dateStringLong = [date formattedDateWithStyle:NSDateFormatterLongStyle];
NSString *dateStringFull = [date formattedDateWithStyle:NSDateFormatterFullStyle];
    
NSLog(@"No: %@", dateStringNo);               //输出:   No:
NSLog(@"Short: %@", dateStringShort);         //输出:   Short: 16/5/23
NSLog(@"Medium: %@", dateStringMedium);       //输出:   Medium: 2016年5月23日
NSLog(@"Long: %@", dateStringLong);           //输出:   Long: 2016年5月23日
NSLog(@"Full: %@", dateStringFull);           //输出:   Full: 2016年5月23日 星期一
    
/**
  *  formattedDateWithFormat(自定义格式)
  */
NSString *dateStringCustom1 = [date formattedDateWithFormat:@"yyyy-MM-dd"];
NSString *dateStringCustom2 = [date formattedDateWithFormat:@"yyyy年MM月dd日"];
NSString *dateStringCustom3 = [date formattedDateWithFormat:@"yyyy-MM-dd HH:mm:ss"];
NSString *dateStringCustom4 = [date formattedDateWithFormat:@"yyyy年MM月dd日 HH:mm:ss"];
NSString *dateStringCustom5 = [date formattedDateWithFormat:@"yyyy年MM月dd日 HH点mm分ss秒"];
    
NSLog(@"Custom1: %@", dateStringCustom1);       //输出:   Custom1: 2016-05-23
NSLog(@"Custom2: %@", dateStringCustom2);       //输出:   Custom2: 2016年05月23日
NSLog(@"Custom3: %@", dateStringCustom3);       //输出:   Custom3: 2016-05-23 13:42:53
NSLog(@"Custom4: %@", dateStringCustom4);       //输出:   Custom4: 2016年05月23日 13:42:53
NSLog(@"Custom5: %@", dateStringCustom5);       //输出:   Custom5: 2016年05月23日 13点42分53秒
  字符  说明                                      
  yy  年的后2位                                   
yyyy 完整年                                     
  M   1~12     月(不带0)                         
  MM  1~12     月(带0)                          
MMM  Jan/Feb/Mar/Apr/May/Jun/Jul/Aug/Sep/Oct/Nov/Dec     (1~12月_简写)
MMMM January/February/March/April/May/June/July/August/September/October/November/December      (1~12月_全写)
  d   1~31     日(不带0)                         
  dd  1~31     日(带0)                          
EEE  Sun/Mon/Tue/Wed/Thu/Fri/Sat     (星期_简写) 
EEEE Sunday/Monday/Tuesday/Wednesday/Thursday/Friday/Saturday     (星期_全写)
  aa  AM/PM     (上午/下午)                       
  H   0~23     时(24小时制,不带0)                   
  HH  0~23     时(24小时制,带0)                    
  h   1~12     时(12小时制,不带0)                   
  hh  1~12     时(24小时制,带0)                    
  m   0~59     分(不带0)                         
  mm  0~59     分(带0)                          
  s   0~59     秒(不带0)                         
  ss  0~59     秒(带0)                          
  S   毫秒                                      

Time Periods「时间段」


DateTools提供DTTimePeriod来简化时间段的操作

初始化和获取时间段信息

/**
  *  通过起始时间来初始化时间段
  */
NSDate *startDate = [NSDate date];
NSDate *endDate = [startDate dateByAddingHours:2];
DTTimePeriod *timePeriod =[[DTTimePeriod alloc] initWithStartDate:startDate endDate:endDate];
    
BOOL hasStartDate = timePeriod.hasStartDate;        //是否有开始时间
BOOL hasEndDate   = timePeriod.hasEndDate;          //是否有结束时间
BOOL isMoment     = timePeriod.isMoment;            //是否开始时间和结束时间相同
    
double  durationInYears   = [timePeriod durationInYears];    //相差年
double  durationInWeeks   = [timePeriod durationInWeeks];    //相差周
double  durationInDays    = [timePeriod durationInDays];     //相差日
double  durationInHours   = [timePeriod durationInHours];    //相差小时
double  durationInMinutes = [timePeriod durationInMinutes];  //相差分
double  durationInSeconds = [timePeriod durationInSeconds];  //相差秒
    
NSLog(@"%f%f%f%f小时 %f%f",durationInYears, durationInWeeks, durationInDays, durationInHours, durationInMinutes, durationInSeconds);
//输出: 0.000000年 0.000000周 0.000000日 2.000000小时 120.000000分 7200.000000秒

更多初始化时间段方法:

更多初始化时间段方法

时间段操作

移动时间段:
shiftEarlierWithSize     时间段整体前移
shiftLaterWithSize       时间段整体后移

/**
  *  移动时间段
  */
NSDate *startDate = [NSDate date];
NSDate *endDate = [startDate dateByAddingDays:2];
DTTimePeriod *timePeriod =[[DTTimePeriod alloc] initWithStartDate:startDate endDate:endDate];
    
NSLog(@"开始:%@", [timePeriod.StartDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
NSLog(@"结束:%@", [timePeriod.EndDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
//输出: 开始:2016年5月23日
//输出: 结束:2016年5月25日
    
[timePeriod shiftEarlierWithSize:DTTimePeriodSizeDay];              //提前1天
    
NSLog(@"开始:%@", [timePeriod.StartDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
NSLog(@"结束:%@", [timePeriod.EndDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
//输出: 开始:2016年5月22日
//输出: 结束:2016年5月24日

[timePeriod shiftLaterWithSize:DTTimePeriodSizeDay amount:2];       //延后2天
    
NSLog(@"开始:%@", [timePeriod.StartDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
NSLog(@"结束:%@", [timePeriod.EndDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
//输出: 开始:2016年5月24日
//输出: 结束:2016年5月26日

延长/缩短时间段:
shortenWithAnchorDate     延长(开始时间/中间时间/结束时间)
lengthenWithAnchorDate   缩短(开始时间/中间时间/结束时间)

/**
  *  时间段延长/缩短
  */
NSDate *startDate = [NSDate date];
NSDate *endDate = [startDate dateByAddingDays:2];
DTTimePeriod *timePeriod =[[DTTimePeriod alloc] initWithStartDate:startDate endDate:endDate];
    
NSLog(@"时长: %.2f", [timePeriod durationInDays]);
//输出: 时长: 2.00天

[timePeriod lengthenWithAnchorDate:DTTimePeriodAnchorEnd size:DTTimePeriodSizeDay amount:1];        //延长1天(增加结束时间)

NSLog(@"时长: %.2f", [timePeriod durationInDays]);
//输出: 时长: 3.00天

[timePeriod shortenWithAnchorDate:DTTimePeriodAnchorStart size:DTTimePeriodSizeDay amount:4];       //缩短4天(减少开始时间)
    
NSLog(@"时长: %.2f", [timePeriod durationInDays]);
//输出: 时长: 0.00天

时间段关系

 >两个时间段关系相关方法:

时间段关系方法

两个时间段关系所有可能性:

时间段关系可能性

时间段关系枚举DTTimePeriodRelation:

/**
  *  DTTimePeriodRelation时间段关系枚举
  */
typedef NS_ENUM(NSUInteger, DTTimePeriodRelation){
    DTTimePeriodRelationAfter,      
    DTTimePeriodRelationStartTouching,    
    DTTimePeriodRelationStartInside,
    DTTimePeriodRelationInsideStartTouching,
    DTTimePeriodRelationEnclosingStartTouching,
    DTTimePeriodRelationEnclosing,
    DTTimePeriodRelationEnclosingEndTouching,
    DTTimePeriodRelationExactMatch,
    DTTimePeriodRelationInside,
    DTTimePeriodRelationInsideEndTouching,
    DTTimePeriodRelationEndInside,
    DTTimePeriodRelationEndTouching,
    DTTimePeriodRelationBefore,
    DTTimePeriodRelationNone      
};

#Time Period Groups「时间段组」

DateTools提供两种时间段组类:
DTTimePeriodCollection     时间段集合 (允许存储彼此有交集的时间段)
DTTimePeriodChain    时间段链接 (不允许存储彼此有交集的时间段)

DTTimePeriodCollection和DTTimePeriodChain就像NSArray一样,你可以像操作数组一样对它们中的DTTimePeriod对象进行添加,插入,删除,不同之处在于如何处理时间段

DTTimePeriodCollection (时间段集合)

 >一个规则相对宽松的时间段集合
默认是无序的,但是支持通过调用方法排序
有自己的属性,例如StartDate和EndDate属性是根据内部时间段推测出来的
允许存储有重叠的时间段

时间段集合

//时间段集合
DTTimePeriodCollection *timePeriodCollection = [DTTimePeriodCollection collection]; 
/**
  *  时间段
  *
  *  当前时间为: 2016年5月24日 
  */
DTTimePeriod *timePeriod1 = [DTTimePeriod timePeriodWithSize:DTTimePeriodSizeDay startingAt:[NSDate date]];
DTTimePeriod *timePeriod2 = [DTTimePeriod timePeriodWithSize:DTTimePeriodSizeDay endingAt:[NSDate date]];
    
NSLog(@"开始:%@ 结束:%@", [timePeriod1.StartDate formattedDateWithStyle:NSDateFormatterMediumStyle], [timePeriod1.EndDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
NSLog(@"开始:%@ 结束:%@", [timePeriod2.StartDate formattedDateWithStyle:NSDateFormatterMediumStyle], [timePeriod2.EndDate formattedDateWithStyle:NSDateFormatterMediumStyle]);
//输出:   开始:2016年5月24日 结束:2016年5月25日
//输出:   开始:2016年5月23日 结束:2016年5月24日
    
/**
 *  时间段集合操作
 */
//添加
[timePeriodCollection addTimePeriod:timePeriod1];
//插入
[timePeriodCollection insertTimePeriod:timePeriod2 atIndex:0];
//移除
[timePeriodCollection removeTimePeriodAtIndex:0];
    
/**
 *  时间段集合排序
 */
//按开始时间升序
[timePeriodCollection sortByStartAscending];
//按开始时间降序
[timePeriodCollection sortByStartDescending];
//按结束时间升序
[timePeriodCollection sortByEndAscending];
//按结束时间降序
[timePeriodCollection sortByEndDescending];
//按持续时间升序
[timePeriodCollection sortByDurationAscending];
//按持续时间降序
[timePeriodCollection sortByDurationDescending];
    
//从时间段集合中获取时间段
DTTimePeriod *firstTimePeriod = [timePeriodCollection objectAtIndexedSubscript:0];

时间段集合操作示意图

获取一个NSDate对象或一个DTTimePeriod对象与一个时间段集合的相对关系

时间段集合操作方法

DTTimePeriodChain (时间链)

一个紧密耦合的时间段集合
通常依据开始时间和结束时间存储时间段对象
有自己的属性,例如StartDate和EndDate属性是根据内部时间段推测出来的 
不允许存储有重叠的时间段

时间链

    
//创建时间链
DTTimePeriodChain *chain = [DTTimePeriodChain chain];
    
//创建时间段
NSDateFormatter * dateFormatter = [[NSDateFormatter alloc]init];
[dateFormatter setDateFormat: @"YYYY MM dd HH:mm:ss.SSS"];
    
DTTimePeriod *firstPeriod = [DTTimePeriod timePeriodWithStartDate:[dateFormatter dateFromString:@"2014 11 05 18:15:12.000"] endDate:[dateFormatter dateFromString:@"2015 11 05 18:15:12.000"]];
DTTimePeriod *secondPeriod = [DTTimePeriod timePeriodWithStartDate:[dateFormatter dateFromString:@"2015 11 05 18:15:12.000"] endDate:[dateFormatter dateFromString:@"2016 11 05 18:15:12.000"]];
    
//添加
[chain addTimePeriod:firstPeriod];
[chain addTimePeriod:secondPeriod];
//插入
[chain insertTimePeriod:firstPeriod atInedx:0];
//移除
[chain removeTimePeriodAtIndex:0];
//移除最晚时间段
[chain removeLatestTimePeriod];
//移除最早时间段
[chain removeEarliestTimePeriod];
    
//获取集合中的元素.
firstPeriod = chain[0];

新加入的时间段,时长不变,起始时间变为前一个时间段的结束时间,结束时间对应前移后后移.在非零位置新插入的时间,其后的时间段相应后移.在零位置插入的时间,集合的起始时间前移

时间链操作示意图

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant