Swift 3-날짜 객체 비교


95

내 앱을 Swift 3.0 구문으로 업데이트하고 있습니다 (아직 베타 버전이지만 출시 되 자마자 준비하고 싶습니다).

엑스 코드 (베타 5)의 이전 베타 때까지 나는이 비교할 수 있었다 Date피연산자를 사용하여 객체를 <, >하고 ==. 그러나 최신 베타 (베타 6)에서는 더 이상 작동하지 않습니다. 다음은 몇 가지 스크린 샷입니다.

여기에 이미지 설명 입력 여기에 이미지 설명 입력

두 스크린 샷에서 볼 수 있듯이 두 Date개체가 있습니다. 하지만 다음과 같은 오류가 발생합니다. 여기에 이미지 설명 입력

내가 뭘 잘못하고 있죠? 함수는 여전히 Date클래스 에서 선언됩니다 .

static func >(Date, Date)

왼쪽 Date가 오른쪽 Date보다 늦은 경우 true를 반환합니다.

이것은 베타 버그입니까, 아니면 내가 뭘 잘못하고 있습니까?


2
let d1 = Date() ; let d2 = Date() ; if d1 > d2 { }내 Xcode 8 베타 6에서 작동합니다.
Martin R

1
예. – 보고서 탐색기에서 전체 오류 메시지를 찾아야합니다.
Martin R

@MartinR 감사합니다! 오류에 "빠져서"더 많은 정보를 얻을 수 있다는 것을 몰랐습니다. 나를 많이 도왔다!
beeef

정답 동의
ANKIT 딴

답변:


161

이 스 니펫 (Xcode 8 Beta 6에서)을 시도했으며 정상적으로 작동합니다.

let date1 = Date()
let date2 = Date().addingTimeInterval(100)

if date1 == date2 { ... }
else if date1 > date2 { ... }
else if date1 < date2 { ... }

시간을 무시하고 싶다면. 예를 들어 2019-05-14 12:08:14 +0000== 2019-05-14는 true를 반환해야합니다. 그리고 뭐 ?
Awais Fayyaz 19-06-12

@AwaisFayyaz DateComponent를 고려하지 않고 날짜를 비교하려는 경우. 날짜부터 원하는 구성 요소를 가져와야합니다. 그런 다음 DateComponents에서 날짜를 가져 와서 비교합니다.
Giorgio Doganiero

52

Dateis Comparable& Equatable(Swift 3 기준)

이 답변은 @Ankit Thakur의 답변을 보완합니다.

Swift 3 이후 Date구조체 (기본 NSDate클래스 기반 )는 ComparableEquatable프로토콜을 채택합니다 .

  • Comparable즉 필요 Date연산자를 구현 : <, <=, >, >=.
  • Equatable운영자 를 Date구현 해야합니다 ==.
  • Equatable연산자 Date의 기본 구현을 사용할 수 있습니다 !=( Equatable ==연산자 구현의 역임).

다음 샘플 코드는 이러한 비교 연산자를 실행하고 print문과 어떤 비교가 참인지 확인 합니다.

비교 기능

import Foundation

func describeComparison(date1: Date, date2: Date) -> String {

    var descriptionArray: [String] = []

    if date1 < date2 {
        descriptionArray.append("date1 < date2")
    }

    if date1 <= date2 {
        descriptionArray.append("date1 <= date2")
    }

    if date1 > date2 {
        descriptionArray.append("date1 > date2")
    }

    if date1 >= date2 {
        descriptionArray.append("date1 >= date2")
    }

    if date1 == date2 {
        descriptionArray.append("date1 == date2")
    }

    if date1 != date2 {
        descriptionArray.append("date1 != date2")
    }

    return descriptionArray.joined(separator: ",  ")
}

샘플 사용

let now = Date()

describeComparison(date1: now, date2: now.addingTimeInterval(1))
// date1 < date2,  date1 <= date2,  date1 != date2

describeComparison(date1: now, date2: now.addingTimeInterval(-1))
// date1 > date2,  date1 >= date2,  date1 != date2

describeComparison(date1: now, date2: now)
// date1 <= date2,  date1 >= date2,  date1 == date2

31

에서 위의 스위프트 3, 날짜 필적 우리가 직접 비교 날짜가 같은 수 있습니다

let date1 = Date()
let date2 = Date().addingTimeInterval(50)

let isGreater = date1 > date2
print(isGreater)

let isSmaller = date1 < date2
print(isSmaller)

let isEqual = date1 == date2
print(isEqual)

또는 날짜에 확장을 만들 수 있습니다.

extension Date {

  func isEqualTo(_ date: Date) -> Bool {
    return self == date
  }
  
  func isGreaterThan(_ date: Date) -> Bool {
     return self > date
  }
  
  func isSmallerThan(_ date: Date) -> Bool {
     return self < date
  }
}

사용하다: let isEqual = date1.isEqualTo(date2)


시간을 무시하고 싶다면. 예를 들어 2019-05-14 12:08:14 +0000== 2019-05-14는 true를 반환해야합니다. 그리고 뭐 ?
Awais Fayyaz 19-06-12

15

http://iswift.org/cookbook/compare-2-dates를 보세요

날짜 가져 오기 :

// Get current date
let dateA = NSDate()

// Get a later date (after a couple of milliseconds)
let dateB = NSDate()

SWITCH 문 사용

// Compare them
switch dateA.compare(dateB) {
    case .OrderedAscending     :   print("Date A is earlier than date B")
    case .OrderedDescending    :   print("Date A is later than date B")
    case .OrderedSame          :   print("The two dates are the same")
}

IF 문 사용

 if dateA.compare(dateB) == .orderedAscending {
     datePickerTo.date = datePicker.date
 }

 //OR

 if case .orderedAcending = dateA.compare(dateB) {

 }

9

나에게 문제는 모든 비교 연산자를 정의하는 Date 클래스에 대한 자체 확장이 있다는 것입니다. 이제 (빠른 3 이후) Date가 비교 가능하므로 이러한 확장이 필요하지 않습니다. 그래서 주석을 달았고 효과가있었습니다.


7

SWIFT 3 : 이것이 당신이 찾고있는 것이 맞는지 모릅니다. 하지만 문자열을 현재 타임 스탬프와 비교하여 내 문자열이 지금보다 오래되었는지 확인합니다.

func checkTimeStamp(date: String!) -> Bool {
        let dateFormatter: DateFormatter = DateFormatter()
        dateFormatter.dateFormat = "yyyy-MM-dd HH:mm:ss"
        dateFormatter.locale = Locale(identifier:"en_US_POSIX")
        let datecomponents = dateFormatter.date(from: date)

        let now = Date()

        if (datecomponents! >= now) {
            return true
        } else {
            return false
        }
    }

그것을 사용하려면 :

if (checkTimeStamp(date:"2016-11-21 12:00:00") == false) {
    // Do something
}

5

날짜를 연도-월-일과 시간없이 비교하려면 다음과 같이 작업했습니다.

     let order = Calendar.current.compare(self.startDate, to: compareDate!, toGranularity: .day)  

                      switch order {
                        case .orderedAscending:
                            print("\(gpsDate) is after \(self.startDate)")
                        case .orderedDescending:
                            print("\(gpsDate) is before \(self.startDate)")
                        default:
                            print("\(gpsDate) is the same as \(self.startDate)")
                        }

5

예를 들어 초를 무시하려면 다음을 사용할 수 있습니다.

func isDate (Date, equalTo : Date, toUnitGranularity : NSCalendar.Unit)-> Bool

같은 날인 경우 비교 예 :

Calendar.current.isDate(date1, equalTo: date2, toGranularity: .day)

1

이 글을 쓰는 시점 기준으로, 스위프트 기본적으로 지원하는 모든 비교 연산자와 날짜를 비교하는 (즉 <, <=, ==, >=, 및 >). 또한 옵션으로 날짜를 비교할 수 있지만, 제한된다 <, ==하고 >. 당신은 사용이 옵션 날짜를 비교해야하는 경우 <=또는 >=, 즉,

let date1: Date? = ...
let date2: Date? = ...
if date1 >= date2 { ... }

<=>=연산자를 오버로드하여 선택 사항을 지원할 수 있습니다 .

func <= <T: Comparable>(lhs: T?, rhs: T?) -> Bool {
    return lhs == rhs || lhs < rhs
}

func >= <T: Comparable>(lhs: T?, rhs: T?) -> Bool {
    return lhs == rhs || lhs > rhs
}

1
extension Date {
 func isBetween(_ date1: Date, and date2: Date) -> Bool {
    return (min(date1, date2) ... max(date1, date2)).contains(self)
  }
}

let resultArray = dateArray.filter { $0.dateObj!.isBetween(startDate, and: endDate) }

1

이를 수행하는 또 다른 방법 :

    switch date1.compare(date2) {
        case .orderedAscending:
            break

        case .orderedDescending:
            break;

        case .orderedSame:
            break
    }

1
   var strDateValidate = ""
            let dateFormatter = DateFormatter()
            dateFormatter.dateFormat = "yyyy-MM-dd"

            let firstDate = dateFormatter.date(from:lblStartTime.text!)
            let secondDate = dateFormatter.date(from:lblEndTime.text!)

            if firstDate?.compare(secondDate!) == .orderedSame || firstDate?.compare(secondDate!) == .orderedAscending {
                print("Both dates are same or first is less than scecond")
                strDateValidate = "yes"
            }
            else
            {
                //second date is bigger than first
                strDateValidate = "no"
            }

            if strDateValidate == "no"
            {
                alertView(message: "Start date and end date for a booking must be equal or Start date must be smaller than the end date", controller: self)
            }

1

스위프트 5 :

1) 날짜 유형을 사용하는 경우 :

let firstDate  = Date()
let secondDate = Date()

print(firstDate > secondDate)  
print(firstDate < secondDate)
print(firstDate == secondDate)

2) 문자열 유형을 사용하는 경우 :

let firstStringDate  = "2019-05-22T09:56:00.1111111"
let secondStringDate = "2019-05-22T09:56:00.2222222"

print(firstStringDate > secondStringDate)  // false
print(firstStringDate < secondStringDate)  // true
print(firstStringDate == secondStringDate) // false 

잘 모르겠거나 두 번째 옵션이 100 %로 작동합니다. 그러나 firstStringDate 및 secondStringDate의 값을 변경하지 않으면 결과가 정확했습니다.


1

Swift 3,4에서는 "Compare"를 사용해야합니다. 예를 들면 :

DateArray.sort { (($0)?.compare($1))! == .orderedDescending }
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.