Cómo obtener la fecha del lunes de la semana actual en forma rápida

Estoy tratando de obtener la fecha del lunes de la semana actual. Esto se trata como el primer día de la semana en mi vista de tabla. También necesito obtener el domingo de la semana actual. Esto se trata como el último día de la semana en mi vista de tabla.

Intento actual:

let date = NSDate() let calendar = NSCalendar.currentCalendar() calendar.firstWeekday = 1 //attempt to changefirstday let dateFormatter = NSDateFormatter() let theDateFormat = NSDateFormatterStyle.ShortStyle let theTimeFormat = NSDateFormatterStyle.ShortStyle dateFormatter.dateStyle = theDateFormat dateFormatter.timeStyle = theTimeFormat let currentDateComponents = calendar.components([.YearForWeekOfYear, .WeekOfYear ], fromDate: date) let startOfWeek = calendar.dateFromComponents(currentDateComponents) print("startOfWeek is \(startOfWeek)") let stringDate = dateFormatter.stringFromDate(startOfWeek!) print("string date is \(stringDate)") //This is returning Sunday's date 

Escribí las extensiones de fecha para obtener la fecha para cierto día de la semana y aquí es lo fácil que es usar con Swift 4,

 Date.today().next(.monday) // Feb 12, 2018 at 12:00 AM Date.today().next(.sunday) // Feb 11, 2018 at 12:00 AM Date.today().previous(.sunday) // Feb 4, 2018 at 12:00 AM Date.today().previous(.monday) // Feb 5, 2018 at 12:00 AM Date.today().previous(.thursday) // Feb 1, 2018 at 12:00 AM Date.today().next(.thursday) // Feb 15, 2018 at 12:00 AM Date.today().previous(.thursday, considerToday: true) // Feb 8, 2018 at 11:04 PM Date.today().next(.monday) .next(.sunday) .next(.thursday) // Feb 22, 2018 at 12:00 AM 

Y aquí está la extensión de fecha para eso,

 extension Date { static func today() -> Date { return Date() } func next(_ weekday: Weekday, considerToday: Bool = false) -> Date { return get(.Next, weekday, considerToday: considerToday) } func previous(_ weekday: Weekday, considerToday: Bool = false) -> Date { return get(.Previous, weekday, considerToday: considerToday) } func get(_ direction: SearchDirection, _ weekDay: Weekday, considerToday consider: Bool = false) -> Date { let dayName = weekDay.rawValue let weekdaysName = getWeekDaysInEnglish().map { $0.lowercased() } assert(weekdaysName.contains(dayName), "weekday symbol should be in form \(weekdaysName)") let searchWeekdayIndex = weekdaysName.index(of: dayName)! + 1 let calendar = Calendar(identifier: .gregorian) if consider && calendar.component(.weekday, from: self) == searchWeekdayIndex { return self } var nextDateComponent = DateComponents() nextDateComponent.weekday = searchWeekdayIndex let date = calendar.nextDate(after: self, matching: nextDateComponent, matchingPolicy: .nextTime, direction: direction.calendarSearchDirection) return date! } } // MARK: Helper methods extension Date { func getWeekDaysInEnglish() -> [String] { var calendar = Calendar(identifier: .gregorian) calendar.locale = Locale(identifier: "en_US_POSIX") return calendar.weekdaySymbols } enum Weekday: String { case monday, tuesday, wednesday, thursday, friday, saturday, sunday } enum SearchDirection { case Next case Previous var calendarSearchDirection: Calendar.SearchDirection { switch self { case .Next: return .forward case .Previous: return .backward } } } } 

Puede usar el calendario ISO8601 donde el primer día de la semana es el lunes:

Swift 3 o posterior

 var mondaysDate: Date { return Calendar(identifier: .iso8601).date(from: Calendar(identifier: .iso8601).dateComponents([.yearForWeekOfYear, .weekOfYear], from: Date()))! } print(mondaysDate.description(with: .current)) // Monday, July 16, 2018 at 12:00:00 AM Brasilia Standard Time" 

como una extensión:

 extension Date { var cureentWeekMonday: Date { return Calendar.iso8601.date(from: Calendar.iso8601.dateComponents([.yearForWeekOfYear, .weekOfYear], from: self))! } } 

 let cureentWeekMonday = Date().cureentWeekMonday print(cureentWeekMonday.description(with: .current)) // Monday, July 16, 2018 at 12:00:00 AM Brasilia Standard Time 

Aquí está la extensión que creé, primero encuentra el domingo y luego agrega un día

 extension Date { var startOfWeek: Date? { let gregorian = Calendar(identifier: .gregorian) guard let sunday = gregorian.date(from: gregorian.dateComponents([.yearForWeekOfYear, .weekOfYear], from: self)) else { return nil } return gregorian.date(byAdding: .day, value: 1, to: sunday) } } 

Tratar de usar:

 calendar.firstWeekday = 2 

Editar

Para ser más específico: NSCalendar.currentCalendar() devuelve el calendario del usuario. De acuerdo con los documentos:

El calendario devuelto se forma a partir de las configuraciones para la configuración regional del sistema elegida por el usuario actual, superpuestas con cualquier configuración personalizada que el usuario haya especificado en Preferencias del Sistema.

Si desea siempre el lunes como primer día, creo que debería usar:

 let calendar = NSCalendar(calendarIdentifier: NSCalendarIdentifierGregorian)! calendar!.firstWeekday = 2 

Aquí hay una versión simplificada de la respuesta de Sandeep .

Uso:

 Date().next(.monday) Date().next(.monday, considerToday: true) Date().next(.monday, direction: .backward) 

Extensión:

 public func next(_ weekday: Weekday, direction: Calendar.SearchDirection = .forward, considerToday: Bool = false) -> Date { let calendar = Calendar(identifier: .gregorian) let components = DateComponents(weekday: weekday.rawValue) if considerToday && calendar.component(.weekday, from: self) == weekday.rawValue { return self } return calendar.nextDate(after: self, matching: components, matchingPolicy: .nextTime, direction: direction)! } public enum Weekday: Int { case sunday = 1, monday, tuesday, wednesday, thursday, friday, saturday } 

Adición a @Saneep respuesta

Si desea obtener la fecha y hora exactas según la fecha dada / actual (digamos que desea convertir la fecha del díaTiempo -> 23-05-2016 12:00:00 a 23-05-2016 05:35:17 ), intente esto :

 func convertDate(date: NSDate, toGivendate: NSDate) -> NSDate { let calendar = NSCalendar.currentCalendar() let comp = calendar.components([.Year, .Month, .Day, .Hour, .Minute, .Second], fromDate: toGivendate) let hour = comp.hour let minute = comp.minute let second = comp.second let dateComp = calendar.components([.Year, .Month, .Day], fromDate: date) let year = dateComp.year let month = dateComp.month let day = dateComp.day let components = NSDateComponents() components.year = year components.month = month components.day = day components.hour = hour components.minute = minute components.second = second let newConvertedDate = calendar.dateFromComponents(components) return newConvertedDate! }