web-dev-qa-db-ja.com

Swift-タイムスタンプが昨日、今日、明日、またはX日前かどうかを確認します

特定のタイムスタンプが今日発生するか、+ 1/-1日になるかを判断する方法を探しています。基本的に、私はこのようなことをしたいです(擬似コード)

IF days_from_today(timestamp) == -1 RETURN 'Yesterday'
ELSE IF days_from_today(timestamp) == 0 RETURN 'Today'
ELSE IF days_from_today(timestamp) == 1 RETURN 'Tomorrow'
ELSE IF days_from_today(timestamp) < 1 RETURN days_from_today(timestamp) + ' days ago'
ELSE RETURN 'In ' + days_from_today(timestamp) + ' ago'

もっとも重要なのは、Swiftにある必要があり、NSDate/NSCalendarオブジェクトに苦労していることです。私はこのような時間差を計算することから始めました:

let calendar = NSCalendar.currentCalendar()
let date = NSDate(timeIntervalSince1970: Double(timestamp))
let timeDifference = calendar.components([.Second,.Minute,.Day,.Hour],
    fromDate: date, toDate: NSDate(), options: NSCalendarOptions())

ただし、.Dayは時刻とタイムスタンプによって異なるため、この方法で比較するのは簡単ではありません。 PHPでは、mktimeを使用して、1日の始まりに基づいて新しい日付を作成します(つまり、mktime(0,0,0))が、それを行う最も簡単な方法はわかりません。迅速。

誰がこれにアプローチする方法について良いアイデアを持っていますか?おそらく、NSDateの拡張機能などが最適でしょうか?

44
Ben

Calendarには、3つのケースすべてのメソッドがあります

func isDateInYesterday(_ date: Date) -> Bool
func isDateInToday(_ date: Date) -> Bool
func isDateInTomorrow(_ date: Date) -> Bool

昨日より前の日を計算するには

func dateComponents(_ components: Set<Calendar.Component>, 
                      from start: Date, 
                          to end: Date) -> DateComponents

[.day]componentsに渡し、結果からdayプロパティを取得します。


これは、時間部分(Swift 3+)を取り除くことで、以前の日付と後の日付のis inも考慮する関数です。

func dayDifference(from interval : TimeInterval) -> String
{
    let calendar = Calendar.current
    let date = Date(timeIntervalSince1970: interval)
    if calendar.isDateInYesterday(date) { return "Yesterday" }
    else if calendar.isDateInToday(date) { return "Today" }
    else if calendar.isDateInTomorrow(date) { return "Tomorrow" }
    else {
        let startOfNow = calendar.startOfDay(for: Date())
        let startOfTimeStamp = calendar.startOfDay(for: date)
        let components = calendar.dateComponents([.day], from: startOfNow, to: startOfTimeStamp)
        let day = components.day!
        if day < 1 { return "\(-day) days ago" }
        else { return "In \(day) days" }
    }
}

あるいは、昨日今日、および明日DateFormatterを使用して、ローカライズされた文字列を無料で取得できます。

func dayDifference(from interval : TimeInterval) -> String
{
    let calendar = Calendar.current
    let date = Date(timeIntervalSince1970: interval)
    let startOfNow = calendar.startOfDay(for: Date())
    let startOfTimeStamp = calendar.startOfDay(for: date)
    let components = calendar.dateComponents([.day], from: startOfNow, to: startOfTimeStamp)
    let day = components.day!
    if abs(day) < 2 {
        let formatter = DateFormatter()
        formatter.dateStyle = .short
        formatter.timeStyle = .none
        formatter.doesRelativeDateFormatting = true
        return formatter.string(from: date)
    } else if day > 1 {
        return "In \(day) days"
    } else {
        return "\(-day) days ago"
    }
}
86
vadian

Swift 3/4/5:

Calendar.current.isDateInToday(yourDate)
Calendar.current.isDateInYesterday(yourDate)
Calendar.current.isDateInTomorrow(yourDate)

さらに:

Calendar.current.isDateInWeekend(yourDate)

一部の国では、週末は土曜日から日曜日とは異なる場合があり、カレンダーによって異なります。

ユーザー更新を追跡するautoupdatingCurrentカレンダーの代わりにcurrentを使用することもできます。同じように使用します:

Calendar.autoupdatingCurrent.isDateInToday(yourDate)

Calendarは、NSCalendarの型エイリアスです。

87
KlimczakM

Swift 4アップデート:

    let calendar = Calendar.current
    let date = Date()

    calendar.isDateInYesterday(date)
    calendar.isDateInToday(date)
    calendar.isDateInTomorrow(date)
17
Edward

NSCalendarには、直接使用できる新しいメソッドがあります。

NSCalendar.currentCalendar().isDateInTomorrow(NSDate())//Replace NSDate() with your date
NSCalendar.currentCalendar().isDateInYesterday()
NSCalendar.currentCalendar().isDateInTomorrow()

お役に立てれば

6
nishith Singh

1)あなたの例によれば、「昨日」、「今日」などのラベルを受け取りたいです。iOSはデフォルトでこれを行うことができます:

https://developer.Apple.com/documentation/foundation/nsdateformatter/1415848-doesrelativedateformatting?language=objc

2)iOSがこれらのラベルを単独で追加しないときにカスタムラベルを計算する場合は、代わりにdoesRelativeDateFormatting == truedoesRelativeDateFormatting == falseの両方で2つのDateFormatterオブジェクトを使用し、結果を比較できます日付文字列が同じか異なる