首页 文章

NSDate从一天开始到一天结束

提问于
浏览
77
-(NSDate *)beginningOfDay:(NSDate *)date
{
    NSCalendar *cal = [NSCalendar currentCalendar];
    NSDateComponents *components = [cal components:( NSMonthCalendarUnit | NSYearCalendarUnit | NSHourCalendarUnit | NSMinuteCalendarUnit | NSSecondCalendarUnit ) fromDate:date];

    [components setHour:0];
    [components setMinute:0];
    [components setSecond:0];

    return [cal dateFromComponents:components];

}

-(NSDate *)endOfDay:(NSDate *)date
{
    NSCalendar *cal = [NSCalendar currentCalendar];
    NSDateComponents *components = [cal components:(  NSMonthCalendarUnit | NSYearCalendarUnit | NSHourCalendarUnit | NSMinuteCalendarUnit | NSSecondCalendarUnit ) fromDate:date];

    [components setHour:23];
    [components setMinute:59];
    [components setSecond:59];

    return [cal dateFromComponents:components];

}

当我打电话:[self endOfDay:[NSDate date]];我得到了本月的第一天......为什么?我使用这两种方法,因为我需要一个从第一个日期的第一秒开始的间隔(beginningOfDay:date1)到第二个日期的最后一秒(endOfDay:Date2)......

17 回答

  • 19

    For swift 4

    var calendar = Calendar.current
        calendar.timeZone = NSTimeZone(abbreviation: "UTC")! as TimeZone
        let dateAtMidnight = calendar.startOfDay(for: Date())
    
        //For End Date
        var components = DateComponents()
        components.day = 1
        components.second = -1
    
        let dateAtEnd = calendar.date(byAdding: components, to: dateAtMidnight)
    
        print("dateAtMidnight :: \(dateAtMidnight)")
        print("dateAtEnd :: \(dateAtEnd!)")
    
  • 28

    在iOS 8中,这非常方便;你可以做:

    let startOfDay = NSCalendar.currentCalendar().startOfDayForDate(date)
    

    为了结束一天的结束,只需使用NSCalendar方法23小时59分59秒,具体取决于您如何定义一天的结束时间 .

    // Swift 2.0
    let components = NSDateComponents()
    components.hour = 23
    components.minute = 59
    components.second = 59
    let endOfDay = NSCalendar.currentCalendar().dateByAddingComponents(components, toDate: startOfDay, options: NSCalendarOptions(rawValue: 0))
    

    Date Math

    Apple iOS NSCalendar Documentation . (参见章节: Calendrical Calculations

    NSCalendar methods discussed by NSHipster .

  • 2

    Swift 4 简单而精确的答案 .

    开始时间:00:00:00

    结束时间:23:59:59.5

    var date = Date() // current date or replace with a specific date
    var calendar = Calendar.current
    let dateAtMidnight = calendar.startOfDay(for: date)
    let dateAtEnd = calendar.date(bySettingHour: 23, minute: 59, second: 59, of: date)
    
  • 4

    Objective-C

    NSCalendar * calendar = [NSCalendar currentCalendar];
    NSDate * startDate = [calendar startOfDayForDate:[NSDate date]];
    NSLog(@"start date is %@", startDate);
    
  • 3

    我对NSDate的Swift扩展:

    Swift 1.2

    extension NSDate {
    
        func beginningOfDay() -> NSDate {
            var calendar = NSCalendar.currentCalendar()
            var components = calendar.components(.CalendarUnitYear | .CalendarUnitMonth | .CalendarUnitDay, fromDate: self)
            return calendar.dateFromComponents(components)!
        }
    
        func endOfDay() -> NSDate {
            var components = NSDateComponents()
            components.day = 1
            var date = NSCalendar.currentCalendar().dateByAddingComponents(components, toDate: self.beginningOfDay(), options: .allZeros)!
            date = date.dateByAddingTimeInterval(-1)!
            return date
        }
    }
    

    Swift 2.0

    extension NSDate {
    
        func beginningOfDay() -> NSDate {
            let calendar = NSCalendar.currentCalendar()
            let components = calendar.components([.Year, .Month, .Day], fromDate: self)
            return calendar.dateFromComponents(components)!
        }
    
        func endOfDay() -> NSDate {
            let components = NSDateComponents()
            components.day = 1
            var date = NSCalendar.currentCalendar().dateByAddingComponents(components, toDate: self.beginningOfDay(), options: [])!
            date = date.dateByAddingTimeInterval(-1)
            return date
        }
    }
    
  • 16

    您在组件中缺少 NSDayCalendarUnit .

  • 3

    您不必将组件设置为零,只需忽略它们:

    -(NSDate *)beginningOfDay:(NSDate *)date
    {
        NSCalendar *calendar = [NSCalendar currentCalendar];
        NSDateComponents *components = [calendar components:NSYearCalendarUnit | NSMonthCalendarUnit | NSDayCalendarUnit fromDate:date];
        return [calendar dateFromComponents:components];
    }
    
  • 4

    对我来说,这里没有任何答案,否则stackoverflow工作的地方 . 为了开始今天,我做到了这一点 .

    NSCalendar * gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSCalendarIdentifierGregorian]; 
    [gregorian setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:0]];    
    NSDateComponents *components = [gregorian components:NSCalendarUnitYear|NSCalendarUnitMonth|NSCalendarUnitDay fromDate:[NSDate date]]; 
    [components setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:0]]; 
    NSDate *beginningOfToday = [gregorian dateFromComponents:components];
    

    请注意 [gregorian setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:0]];[components setTimeZone:[NSTimeZone timeZoneForSecondsFromGMT:0]]; .

    创建日历时,它会使用当前时区进行初始化,并且从其组件中提取日期时,由于NSDate没有时区,因此从当前时区开始的日期将被视为UTC时区 . 因此,我们需要在提取组件之前设置时区,然后在从这些组件中提取日期时设置时区 .

  • 1

    iOS 8.0+ / macOS 10.12+ / tvOS 10.0+ / watchOS 3.0+ 以来,基金会内置了一个内置功能,您可以直接使用它 . 无需实现自己的功能 .

    public func startOfDay(for date: Date) -> Date

    所以你可以这样使用它:

    let midnightDate = Calendar(identifier: .gregorian).startOfDay(for: Date())

    值得记住的是,这需要考虑设备时区 . 如果您想拥有例如UTC区域,可以在 calendar 上设置 .timeZone .

    链接到Apple参考页面:https://developer.apple.com/reference/foundation/nscalendar/1417161-startofday .

  • 2

    只是使用 dateInterval(of:start:interval:for:) Calendar 的另一种方式

    返回 startDate 包含当天的开始, interval 包含当天的秒数 .

    func startAndEnd(of date : Date) -> (start : Date, end : Date) {
        var startDate = Date()
        var interval : TimeInterval = 0.0
        Calendar.current.dateInterval(of: .day, start: &startDate, interval: &interval, for: date)
        var endDate = startDate.addingTimeInterval(interval-1)
        return (start : startDate, end : endDate)
    }
    
    let (start, end) = startAndEnd(of: Date())
    print(start, end)
    
  • 11

    获得结果的另一种方法:

    NSDate *date = [NSDate date];
    
    NSDateComponents *components = [[NSDateComponents alloc] init];
    components.day = [[NSCalendar currentCalendar] ordinalityOfUnit:(NSCalendarUnitDay) inUnit:(NSCalendarUnitEra) forDate:date];
    NSDate *dayBegin = [[NSCalendar currentCalendar] dateFromComponents:components];
    
    components.day += 1;
    NSDate *dayEnd = [[NSCalendar currentCalendar] dateFromComponents:components];
    
  • 1

    Swift 3

    class func today() -> NSDate {
            return NSDate()
        }
    
        class func dayStart() -> NSDate {
              return NSCalendar.current.startOfDay(for: NSDate() as Date) as NSDate
        }
    
        class func dayEnd() -> NSDate {
            let components = NSDateComponents()
            components.day = 1
            components.second = -1
            return NSCalendar.current.date(byAdding: components as DateComponents, to: self.dayStart() as Date)
        }
    
  • 0
    extension Date {
        func stringFrom(dateFormat: String) -> String {
            let formatter = DateFormatter()
            formatter.dateFormat = dateFormat
            return formatter.string(from: self)
        }
    
        func firstSecondInDay() -> Date {
            let dayStr = self.stringFrom(dateFormat: "yyyy-MM-dd")
            let firstSecondStr = "\(dayStr) 00:00:00"
            let format = DateFormatter()
            format.dateFormat = "yyyy-MM-dd HH:mm:ss"
            return format.date(from: firstSecondStr)!
        }
    
        func lastSecondInDay() -> Date {
            let dayStr = self.stringFrom(dateFormat: "yyyy-MM-dd")
            let laseSecondStr = "\(dayStr) 23:59:59"
            let format = DateFormatter()
            format.dateFormat = "yyyy-MM-dd HH:mm:ss"
            return format.date(from: laseSecondStr)!
        }
    }
    
  • 1

    一天的开始/一天的结束 - 斯威夫特4

    // Extension
    
    extension Date {
        var startOfDay: Date {
            return Calendar.current.startOfDay(for: self)
        }
    
        var endOfDay: Date {
            var components = DateComponents()
            components.day = 1
            components.second = -1
            return Calendar.current.date(byAdding: components, to: startOfDay)!
        }
    
        var startOfMonth: Date {
            let components = Calendar.current.dateComponents([.year, .month], from: startOfDay)
            return Calendar.current.date(from: components)!
        }
    
        var endOfMonth: Date {
            var components = DateComponents()
            components.month = 1
            components.second = -1
            return Calendar.current.date(byAdding: components, to: startOfMonth)!
        }
    }
    
    // End of day = Start of tomorrow minus 1 second
    // End of month = Start of next month minus 1 second
    
  • 14

    你错过了 NSDayCalendarUnit in

    NSDateComponents *components = [cal components:( NSMonthCalendarUnit | NSYearCalendarUnit | NSHourCalendarUnit | NSMinuteCalendarUnit | NSSecondCalendarUnit ) fromDate:date];
    
  • 0

    Swift 4.2 - XCode 10Date 类而不是 NSDateCalender 而不是 NSCalender

    extension Date {
    
        var startOfDay : Date {
            let calendar = Calendar.current
            let unitFlags = Set<Calendar.Component>([.year, .month, .day])
            let components = calendar.dateComponents(unitFlags, from: self)
            return calendar.date(from: components)!
       }
    
        var endOfDay : Date {
            var components = DateComponents()
            components.day = 1
            let date = Calendar.current.date(byAdding: components, to: self.startOfDay)
            return (date?.addingTimeInterval(-1))!
        }
    }
    

    用法:

    let myDate = Date()
        let startOfDate = myDate.startOfDay
        let endOfDate = myDate.endOfDay
    
  • 153

    Swift3 使用 *XCode8
    Apple正在从类名中删除 NS ,以便 NSDate 可以换出 Date . 如果你试图让他们说他们总是会失败,你可能会得到一个编译器警告,但是当他们在操场上运行它们时它们工作正常 .

    我用 Date 替换了我在核心数据模型中生成的 NSDate ,它们仍然可以工作 .

    extension Date {
      func startTime() -> Date {
        return Calendar.current.startOfDay(for: self)
      }
    
      func endTime() -> Date {
        var components = DateComponents()
        components.day = 1
        components.second = -1
        return Calendar.current.date(byAdding: components, to: startTime())!
      }
    }
    

相关问题