I'm trying to calculate the number of weeks and days that a pet is alive. I'm using SwiftDate for that. So I let the user select a birthdate and compare it to the current date.
I don't want to compare the time... so both the birthdate and current date should have the same time.
My code is:
let greg = Calendar(identifier: .gregorian)
var date1 = birthday // from datepicker
var date2 = Date()
var components1 = greg.dateComponents([.year, .month, .day, .hour, .minute, .second], from: date1)
var components2 = greg.dateComponents([.year, .month, .day, .hour, .minute, .second], from: date2)
components1.hour = 15
components1.minute = 0
components1.second = 0
components2.hour = 15
components2.minute = 0
components2.second = 0
date1 = greg.date(from: components1)!
date2 = greg.date(from: components2)!
let daysAlive = (date2 - date1).in(.day)
let weeksAlive = Int(weeksAlive! / 7)
let restDays = daysAlive! - (weeksAlive * 7)
let aLive = "Age: \(weeksAlive) wk, \(restDays) d (\(daysAlive!) d)"
Output is "Age: 28 wk, 3 d (199 d)"
The code works... but how can I refactor it? And is there an easier way to set the 'same time' for two given dates?
To ignore the time just omit the components for .hour
, .minute
and .second
let components1 = greg.dateComponents([.year, .month, .day], from: date1)
let components2 = greg.dateComponents([.year, .month, .day], from: date2)
date1 = greg.date(from: components1)!
date2 = greg.date(from: components2)!
This is a simpler solution without any third party library. It calculates the difference once for weekOfMonth
and day
and once for day
with the Calendar
method dateComponents(:from:to:
. Extra math is not needed.
let greg = Calendar(identifier: .gregorian)
var date1 = greg.date(from: DateComponents(year: 2017, month: 6, day: 25))!
var date2 = Date()
var components1 = greg.dateComponents([.year, .month, .day], from: date1)
var components2 = greg.dateComponents([.year, .month, .day], from: date2)
let weeksAndDays = greg.dateComponents([.weekOfMonth, .day], from: components1, to: components2)
let justDays = greg.dateComponents([.day], from: components1, to: components2)
let aLive = "Age: \(weeksAndDays.weekOfMonth!) wk, \(weeksAndDays.day!) d (\(justDays.day!) d)"
// "Age: 28 wk, 3 d (199 d)"