web-dev-qa-db-ja.com

時間コンポーネントなしのNSDatesの比較

Swift=プレイグラウンドでは、私は

NSDate.date() 

ただし、これは常に時間要素が追加されて表示されます。私のアプリでは、時間要素を無視する必要があります。これはSwiftで可能ですか?どうすればできますか?時間要素をすべての日付で同じ時刻に設定できたとしても、それでも機能します。

また、私は2つの日付を比較しようとしていますが、現時点では次のコードを使用しています:

var earlierDate:NSDate = firstDate.earlierDate(secondDate)

これが唯一の方法ですか、時間要素を無視する方法でこれを行うことはできますか?たとえば、同じ日でも時間は異なる場合、結果は必要ありません。

52
agf119105

このCalendar関数を使用して、iOS 8.0以降の日付を比較します

func compare(_ date1: Date, to date2: Date, toGranularity component: Calendar.Component) -> ComparisonResult


合格.day単位として

この関数は次のように使用します。

let now = Date()
// "Sep 23, 2015, 10:26 AM"
let olderDate = Date(timeIntervalSinceNow: -10000)
// "Sep 23, 2015, 7:40 AM"

var order = Calendar.current.compare(now, to: olderDate, toGranularity: .hour)

switch order {
case .orderedDescending:
    print("DESCENDING")
case .orderedAscending:
    print("ASCENDING")
case .orderedSame:
    print("SAME")
}

// Compare to hour: DESCENDING

var order = Calendar.current.compare(now, to: olderDate, toGranularity: .day)


switch order {
case .orderedDescending:
    print("DESCENDING")
case .orderedAscending:
    print("ASCENDING")
case .orderedSame:
    print("SAME")
}

// Compare to day: SAME
109
Ashley Mills

IOS 8.0以降のNSCalendarには、いくつかの便利なメソッドがあります。

startOfDayForDate, isDateInToday, isDateInYesterday, isDateInTomorrow

また、日を比較する場合でも:

func isDate(date1: NSDate!, inSameDayAsDate date2: NSDate!) -> Bool

時間要素を無視するには、これを使用できます:

var toDay = Calendar.current.startOfDay(for: Date())

ただし、iOS 7もサポートする必要がある場合は、いつでも拡張機能を記述できます

extension NSCalendar {
    func myStartOfDayForDate(date: NSDate!) -> NSDate!
    {
        let systemVersion:NSString = UIDevice.currentDevice().systemVersion
        if systemVersion.floatValue >= 8.0 {
            return self.startOfDayForDate(date)
        } else {
            return self.dateFromComponents(self.components(.CalendarUnitYear | .CalendarUnitMonth | .CalendarUnitDay, fromDate: date))
        }
    }
}
16
slamor

Ashley Millsのソリューションから借用して、2つの日付を比較する次のメソッドを作成しました。 2つの日付を比較し、2つの日付が同じ場合(時刻が削除された場合)、trueを返します。

func compareDate(date1:NSDate, date2:NSDate) -> Bool {
    let order = NSCalendar.currentCalendar().compareDate(date1, toDate: date2,
        toUnitGranularity: .Day)
    switch order {
    case .OrderedSame:
        return true
    default:
        return false
    }
}

そして、それは次のように呼ばれます:

if compareDate(today, date2: anotherDate) {
    // The two dates are on the same day.
}
8
Emmett Corman

In Swift 4:

func compareDate(date1:Date, date2:Date) -> Bool {
    let order = NSCalendar.current.compare(date1, to: date2, toGranularity: .day)
    switch order {
    case .orderedSame:
        return true
    default:
        return false
    }
}
7
zs2020

Swiftでの2つの日付比較。

    // Date comparision to compare current date and end date.
    var dateComparisionResult:NSComparisonResult = currentDate.compare(endDate)

    if dateComparisionResult == NSComparisonResult.OrderedAscending
    {
        // Current date is smaller than end date.
    }
    else if dateComparisionResult == NSComparisonResult.OrderedDescending
    {
        // Current date is greater than end date.
    }
    else if dateComparisionResult == NSComparisonResult.OrderedSame
    {
        // Current date and end date are same.
    }
6
abhi

説明を使用して2つの日付を比較できます。

let date1 = NSDate()
let date2 = NSDate(timeIntervalSinceNow: 120)
if date1.description == date2.description {
    print(true)
} else {
    print(false)   // false (I have added 2 seconds between them)
}

日付の時刻要素を別の時刻に設定したい場合は、次のようにします:

extension NSDate {
    struct Calendar {
        static let gregorian = NSCalendar(calendarIdentifier: NSCalendarIdentifierGregorian)!
    }
    var day:    Int { return Calendar.gregorian.component(.Day,    fromDate: self)   }
    var month:  Int { return Calendar.gregorian.component(.Month,  fromDate: self)  }
    var year:   Int { return Calendar.gregorian.component(.Year,   fromDate: self)  }

    var noon: NSDate {
        return Calendar.gregorian.dateWithEra(1, year: year, month: month, day: day, hour: 12, minute: 0, second: 0, nanosecond: 0)!
    }
}

let date1 = NSDate()
let date2 = NSDate(timeIntervalSinceNow: 120)
print(date1.noon == date2.noon)   // true

またはNSDateFormatterを使用して行うこともできます:

extension NSDate {
    struct Date {
        static let formatterYYYYMMDD: NSDateFormatter = {
            let formatter = NSDateFormatter()
            formatter.dateFormat = "yyyyMMdd"
            return formatter
        }()
    }
    var yearMonthDay: String {
        return Date.formatterYYYYMMDD.stringFromDate(self)
    }
    func isSameDayAs(date:NSDate) -> Bool {
        return yearMonthDay == date.yearMonthDay
    }
}

let date1 = NSDate()
let date2 = NSDate(timeIntervalSinceNow: 120)
print(date1.yearMonthDay == date2.yearMonthDay)   // true

print(date1.isSameDayAs(date2))    // true

別のオプション(iOS8 +)は、カレンダーメソッドisDate(inSameDayAsDate :)を使用することです。

extension NSDate {
    struct Calendar {
        static let gregorian = NSCalendar(calendarIdentifier: NSCalendarIdentifierGregorian)!
    }
    func isInSameDayAs(date date: NSDate) -> Bool {
        return Calendar.gregorian.isDate(self, inSameDayAsDate: date)
    }
}
let date1 = NSDate()
let date2 = NSDate(timeIntervalSinceNow: 120)
if date1.isInSameDayAs(date: date2 ){
    print(true)   // true
} else {
    print(false)
}
4
Leo Dabus

IOS7サポートの場合

let dateFormatter = NSDateFormatter()
dateFormatter.dateFormat = "yyyy-MM-dd"
let date1String = dateFormatter.stringFromDate(date1)
let date2String = dateFormatter.stringFromDate(date2)
if date1String == date2String {
    println("Equal date")
}
4
Loganathan

Swift3の場合

var order = NSCalendar.current.compare(firstDate, to: secondDate, toGranularity: .hour)

if order == .orderedSame {
    //Both the dates are same. 
    //Your Logic.
}
3
Uzma

Swift

        let order = NSCalendar.current.compare(date1, to: date2, toGranularity: .day)

        if order == .orderedAscending { 
          // date 1 is older
        }
        else if order == .orderedDescending { 
          // date 1 is newer
        }
        else if order == .orderedSame { 
          // same day/hour depending on granularity parameter
        }
2

2つの日付を比較するためにSwift 4の拡張機能を作成しました。

_import Foundation

extension Date {      
  func isSameDate(_ comparisonDate: Date) -> Bool {
    let order = Calendar.current.compare(self, to: comparisonDate, toGranularity: .day)
    return order == .orderedSame
  }

  func isBeforeDate(_ comparisonDate: Date) -> Bool {
    let order = Calendar.current.compare(self, to: comparisonDate, toGranularity: .day)
    return order == .orderedAscending
  }

  func isAfterDate(_ comparisonDate: Date) -> Bool {
    let order = Calendar.current.compare(self, to: comparisonDate, toGranularity: .day)
    return order == .orderedDescending
  }
}
_

使用法:

startDate.isSameDateAs(endDate) // returns a true or false

2
Adrian

迅速:

extension NSDate {

    /**
    Compares current date with the given one down to the seconds.
    If date==nil, then always return false

    :param: date date to compare or nil

    :returns: true if the dates has equal years, months, days, hours, minutes and seconds.
    */
    func sameDate(date: NSDate?) -> Bool {
        if let d = date {
            let calendar = NSCalendar.currentCalendar()
            if NSComparisonResult.OrderedSame == calendar.compareDate(self, toDate: d, toUnitGranularity: NSCalendarUnit.SecondCalendarUnit) {
                return true
            }

        }
        return false
    }
}
1

スイフト4

func compareDate(date1:Date, date2:Date) -> Bool {
    let order = Calendar.current.compare(date1, to: date2,toGranularity: .day)
    switch order {
    case .orderedSame:
        return true
    default:
        return false
    }
}
0
Asad Jamil

私の経験では、NSDateの使用に関するほとんどの人の問題は、NSDateを使用して「通常」の意味で日付を表すことができるという誤った想定に起因しています(つまり、ローカルタイムゾーンの午前0時に始まる24期間)。通常の(毎日/非プログラミング)使用では、ロンドンの2014年1月1日は、北京またはニューヨークの1月1日と同じ日付ですリアルタイムで異なる期間をカバーしている場合でも。これを極端にするために、クリスマス島の時間はUTC + 14で、ミッドウェイ島の時間はUTC-11です。したがって、これら2つの島の2014年1月1日は、一方がもう1時間完了するまで開始しなくても、同じ日付です。

それが記録する日付の種類である場合(および時間コンポーネントを記録していない場合は、おそらくそうです)、NSDate(2001-01-01 00:00 UTCを過ぎた秒のみを保存し、それ以外は何も保存しない)を使用しないでくださいしかし、おそらくこれらの値をラップする独自のCivilDateクラスを作成して、年月日を整数として保存し、代わりにそれを使用します。

NSDateのみを使用して日付を比較し、比較のために両方のNSDateでタイムゾーンを明示的に「UTC」として宣言するようにしてください。

0

プレイグラウンドでNSDate.date()を実行すると、デフォルトの説明が表示されます。 NSDateFormatterを使用して、日付オブジェクトのローカライズされた説明を(場合によっては日付部分のみで)印刷します。

(比較のために)日付の特定の部分をゼロにするには、NSDateComponentsとともにNSCalendarを使用します。

0
Leo Natan