Jak dodać miesiąc do obiektu NSDate?
NSDate *someDate = [NSDate Date] + 30Days.....;
ios
iphone
objective-c
nsdate
lub azran
źródło
źródło
Odpowiedzi:
Musisz użyć NSDateComponents :
NSDateComponents *dateComponents = [[NSDateComponents alloc] init]; [dateComponents setMonth:1]; NSCalendar *calendar = [NSCalendar currentCalendar]; NSDate *newDate = [calendar dateByAddingComponents:dateComponents toDate:originalDate options:0]; [dateComponents release]; // If ARC is not used, release the date components
źródło
[date timeIntervalSinceDate:otherDate]
co zwróci różnicę między nimi w sekundach (mniej niż 0 dla dat przeszłych, większe niż 0 dla dat przyszłych).W systemie iOS 8 i OS X 10.9 możesz dodać
NSCalendarUnits
za pomocąNSCalendar
:Cel C
NSCalendar *cal = [NSCalendar currentCalendar]; NSDate *someDate = [cal dateByAddingUnit:NSCalendarUnitMonth value:1 toDate:[NSDate date] options:0];
Szybki 3
let date = Calendar.current.date(byAdding: .month, value: 1, to: Date())
Szybki 2
let cal = NSCalendar.currentCalendar() let date = cal.dateByAddingUnit(.Month, value: 1, toDate: NSDate(), options: [])
źródło
Dla Swift 3.0
extension Date { func addMonth(n: Int) -> Date { let cal = NSCalendar.current return cal.date(byAdding: .month, value: n, to: self)! } func addDay(n: Int) -> Date { let cal = NSCalendar.current return cal.date(byAdding: .day, value: n, to: self)! } func addSec(n: Int) -> Date { let cal = NSCalendar.current return cal.date(byAdding: .second, value: n, to: self)! } }
źródło
Na przykład, aby dodać
3
miesiące do bieżącej daty w Swift:let date = NSCalendar.currentCalendar().dateByAddingUnit(.MonthCalendarUnit, value: 3, toDate: NSDate(), options: nil)!
W Swift 2.0:
let date = NSCalendar.currentCalendar().dateByAddingUnit(.Month, value: 3, toDate: NSDate(), options: [])
OptionSetType
strukturaNSCalendarUnit
umożliwia prostsze określenie.Month
OptionSetType
(takie jakoptions:
parametr, który przyjmujeNSCalendarOptions
) nie mogą byćnil
, więc przekaż puste zestaw ([]
), aby reprezentować „brak opcji”.źródło
.MonthCalendarUnit
jest przestarzałe, użyj.CalendarUnitMonth
W Swift 2.0
let startDate = NSDate() let dateComponent = NSDateComponents() dateComponent.month = 1 let cal = NSCalendar.currentCalendar() let endDate = cal.dateByAddingComponents(dateComponent, toDate: startDate, options: NSCalendarOptions(rawValue: 0))
źródło
DLA SWIFT 3.0
tutaj jest funkcja, możesz zredukować dni, miesiące, dni o dowolną liczbę, jak na przykład tutaj, zmniejszyłem rok bieżącej daty systemowej o 100 lat, możesz to zrobić dla dnia, miesiąca również po prostu ustaw licznik, a następnie zapisz wartości w tablicy i zrób z nią co chcesz
func currentTime(){ let date = Date() let calendar = Calendar.current var year = calendar.component(.year, from: date) let month = calendar.component(.month, from: date) let day = calendar.component(.day, from: date) let pastyear = year - 100 var someInts = [Int]() printLog(msg: "\(day):\(month):\(year)" ) for _ in pastyear...year { year -= 1 print("\(year) ") someInts.append(year) } print(someInts) }
źródło
Inne odpowiedzi działają dobrze, jeśli Twoim pożądanym zachowaniem jest dodanie miesiąca i uwzględnienie czasu letniego. Daje to takie wyniki, że:
01/03/2017 00:00 + 1 month -> 31/03/2017 23:00 01/10/2017 00:00 + 1 month -> 01/11/2017 01:00
Jednak chciałem zignorować godzinę straconą lub zyskowną przez DST, tak że:
01/03/2017 00:00 + 1 month -> 01/04/2017 00:00 01/10/2017 00:00 + 1 month -> 01/11/2017 00:00
Więc sprawdzam, czy granica czasu letniego została przekroczona, a jeśli tak, to odpowiednio dodaj lub odejmij godzinę:
func offsetDaylightSavingsTime() -> Date { // daylightSavingTimeOffset is either + 1hr or + 0hr. To offset DST for a given date, we need to add an hour or subtract an hour // +1hr -> +1hr // +0hr -> -1hr // offset = (daylightSavingTimeOffset * 2) - 1 hour let daylightSavingsTimeOffset = TimeZone.current.daylightSavingTimeOffset(for: self) let oneHour = TimeInterval(3600) let offset = (daylightSavingsTimeOffset * 2) - oneHour return self.addingTimeInterval(offset) } func isBetweeen(date date1: Date, andDate date2: Date) -> Bool { return date1.compare(self).rawValue * self.compare(date2).rawValue >= 0 } func offsetDaylightSavingsTimeIfNecessary(nextDate: Date) -> Date { if let nextDST = TimeZone.current.nextDaylightSavingTimeTransition(after: self) { if nextDST.isBetweeen(date: self, andDate: nextDate){ let offsetDate = nextDate.offsetDaylightSavingsTime() let difference = offsetDate.timeIntervalSince(nextDate) return nextDate.addingTimeInterval(difference) } } return nextDate } func dateByAddingMonths(_ months: Int) -> Date? { if let dateWithMonthsAdded = Calendar.current.date(byAdding: .month, value: months, to: self) { return self.offsetDaylightSavingsTimeIfNecessary(nextDate: dateWithMonthsAdded) } return self }
Test:
func testDateByAddingMonths() { let date1 = "2017-01-01T00:00:00Z".asDate() let date2 = "2017-02-01T00:00:00Z".asDate() let date3 = "2017-03-01T00:00:00Z".asDate() let date4 = "2017-04-01T00:00:00Z".asDate() let date5 = "2017-05-01T00:00:00Z".asDate() let date6 = "2017-06-01T00:00:00Z".asDate() let date7 = "2017-07-01T00:00:00Z".asDate() let date8 = "2017-08-01T00:00:00Z".asDate() let date9 = "2017-09-01T00:00:00Z".asDate() let date10 = "2017-10-01T00:00:00Z".asDate() let date11 = "2017-11-01T00:00:00Z".asDate() let date12 = "2017-12-01T00:00:00Z".asDate() let date13 = "2018-01-01T00:00:00Z".asDate() let date14 = "2018-02-01T00:00:00Z".asDate() var testDate = "2017-01-01T00:00:00Z".asDate() XCTAssertEqual(testDate, date1) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date2) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date3) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date4) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date5) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date6) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date7) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date8) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date9) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date10) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date11) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date12) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date13) testDate = testDate.dateByAddingMonths(1)! XCTAssertEqual(testDate, date14) }
Aby uzyskać kompletność, używam metody .asDate ()
extension String { static let dateFormatter = DateFormatter() func checkIsValidDate() -> Bool { return self.tryParseToDate() != nil } func tryParseToDate() -> Date? { String.dateFormatter.dateFormat = "yyyy-MM-dd'T'HH:mm:ssZZZZZ" return String.dateFormatter.date(from: self) } func asDate() -> Date { return tryParseToDate()! } }
źródło
Czy chcesz dodać „miesiąc” czy dokładnie 30 dni lub jeden dzień lub rok w oparciu o wybór przez użytkownika automatycznego obliczania do dnia.
NSCalendar *calendar = [NSCalendar currentCalendar]; NSDateFormatter *dateFormatter = [[NSDateFormatter alloc] init]; [dateFormatter setDateFormat:@"YYYY-MM-dd HH:mm:ss"]; NSDateComponents *components = [calendar components:(NSCalendarUnitHour | NSCalendarUnitMinute) fromDate:[NSDate date]]; NSDateComponents *dayComponent = [[NSDateComponents alloc] init]; int changeid = [here number of days intValue]; dayComponent.hour = changeid; NSCalendar *theCalendar = [NSCalendar currentCalendar]; NSDate *nextDate = [theCalendar dateByAddingComponents:dayComponent toDate:[dateFormatter dateFromString:self.fromDateTF.text] options:0]; NSLog(@"nextDate: %@ ...", nextDate); [self.toDateTF setText:[dateFormatter stringFromDate:nextDate]];
////miesiąc
źródło
Chcesz dodać „miesiąc” czy dokładnie 30 dni? Jeśli to 30 dni, robisz to w ten sposób:
// get a date NSDate *date = [NSDate dateWithNaturalLanguageString:@"2011-01-02"]; // add 30 days to it (in seconds) date = [date dateByAddingTimeInterval:(30 * 24 * 60 * 60)]; NSLog(@"%@", date); // 2011-02-01
Uwaga: nie będzie to uwzględniać zmian czasu letniego ani sekund przestępnych. Użyj odpowiedzi @ TheEye, jeśli tego potrzebujesz
źródło