swift 如何检查日期是否介于两个日期之间而不考虑年份

n3ipq98p  于 2022-11-21  发布在  Swift
关注(0)|答案(3)|浏览(129)

我如何检查是否有任何日期介于两个日期之间?例如,我想检查当前日期是否介于12月15日和1月15日之间。
这可以是任何一年,所以我的当前日期可以是2023年12月15日,它应该返回true。如果是12月14日或任何一年的1月16日,它应该返回false。12月31日应该返回true。
这就是我所尝试的:

let now = currentDateProvider()
dateFormatter.dateFormat = "yyyy-MM-dd"
let year = Calendar.current.component(.year, from: now)
guard let start = dateFormatter.date(from: "\(year)-01-01"),
      let end = dateFormatter.date(from: "\(year)-01-07") else {
   return false
}
if start <= now && now <= end {
    return true
}

guard let start = dateFormatter.date(from: "\(year)-12-01"),
      let end = dateFormatter.date(from: "\(year)-12-31") else {
    return false
}
let value = start <= now && now <= end
return value

但它似乎有点错误,因为如果我的时区是UTC +2,那么结束日期给我12月30日22:00:00,因为UTC + 2是12月31日00:00 - 2小时,它给你12月30日,而不是31日。
理想的情况下,我不想分开检查的日期,只是有一个包括检查12月15日和1月15日之间,而不是检查12月15日至12月31日和1月1日至1月7日。

n3h0vuf2

n3h0vuf21#

我将获取日期的月和日的日期组件,并对这些值进行简单的比较

let components = Calendar.current.dateComponents([.month, .day], from: date)
let inPeriod = (components.month! == 12 && components.day! >= 15) || (components.month! == 1 && components.day! <= 15)

简单测试用例

var testDate = Calendar.current.date(from: DateComponents(calendar: .current, year: 2021, month: 12, day: 14))!

for _ in 1...34 {
    let components = Calendar.current.dateComponents([.month, .day], from: testDate)
    print(testDate, (components.month! == 12 && components.day! >= 15) || (components.month! == 1 && components.day! <= 15))
    testDate = Calendar.current.date(byAdding: .day, value: 1, to: testDate)!
}
whlutmcx

whlutmcx2#

您不能忽略年份,尤其是当年份的转折点在区间内时。由于实际上涉及到当前日期,您希望检查该日期是否在当前年的12月和年的1月之间
我的建议是从当前日期获取年组件,然后通过将月设置为12、日设置为15来构建开始日期,并通过向指向下一年1月16日的开始日期添加一天和一个月来构建结束日期。

let currentDate = Date.now
let year = Calendar.current.component(.year, from: currentDate)
let startComponents = DateComponents(year: year, month: 12, day: 15)
let startDate = Calendar.current.date(from: startComponents)!
let endDate = Calendar.current.date(byAdding: DateComponents(month: 1, day: 1), to: startDate)!

if currentDate >= startDate && currentDate < endDate {
    print("isValid")
}
zmeyuzjn

zmeyuzjn3#

我要赎罪!
1.没有看到您正在寻找一个考虑到您所在时区的解决方案
1.没看到你想要的东西只对间隔感兴趣,而不是在年。
我得承认,有时候我看书时没有注意到问题,特别是那些我认为很容易的问题。
希望下面的解决方案能满足你的需要。就像其他学院说的,你不可能不考虑年份,但是你可以像你一样在函数里面模拟年份。
请自己看一看,看看您是更喜欢我的解决方案,还是坚持使用您的解决方案:

import Foundation

let f = ISO8601DateFormatter()
f.formatOptions = .withFullDate
f.timeZone = TimeZone(abbreviation: "PST")

func thisDate(_ date: Date, isBetweenthisMonth initialMonth: Int, andDay initialDay: Int, andThisOtherMonth finalMonth: Int, andThisOtherDay finalDay: Int) -> Bool {
    var isBetween = false
    
    let year = Calendar.current.component(.year, from: date)
    
    let initialYear = year
    var finalYear = year
    
    if finalMonth < initialMonth {
        finalYear += finalYear
    }
    
    let initialFakeData = f.date(from: "\(initialYear)-\(initialMonth)-\(initialDay)")!
    let finalFakeData = f.date(from: "\(finalYear)-\(finalMonth)-\(finalDay)")!
    
    if (date > initialFakeData && date < finalFakeData) {
        isBetween = true
    }
    
    return isBetween
}

// Some test cases to pass
let date = f.date(from: "2022-11-01")!

print(thisDate(date, isBetweenthisMonth: 12, andDay: 02, andThisOtherMonth: 02, andThisOtherDay: 23) == false ? "False" : "Something wrong.")
print(thisDate(date, isBetweenthisMonth: 10, andDay: 02, andThisOtherMonth: 01, andThisOtherDay: 15) == true ? "True" : "Something wrong.")

let date2 = f.date(from: "2022-12-31")!

print(thisDate(date2, isBetweenthisMonth: 12, andDay: 30, andThisOtherMonth: 01, andThisOtherDay: 01) == true ? "True" : "Something wrong.")
print(thisDate(date2, isBetweenthisMonth: 01, andDay: 01, andThisOtherMonth: 01, andThisOtherDay: 15) == false ? "False" : "Something wrong.")

let date_now = f.date(from: f.string(from: Date()))!

print(thisDate(date_now, isBetweenthisMonth: 11, andDay: 08, andThisOtherMonth: 11, andThisOtherDay: 10) == true ? "True" : "Something wrong.")
print(thisDate(date_now, isBetweenthisMonth: 12, andDay: 01, andThisOtherMonth: 02, andThisOtherDay: 01) == false ? "False" : "Something wrong.")

我不知道如何使用XCTest进入游戏场,所以我在最后的代码中模拟了一些测试。

相关问题