在 android 中以 15 分钟的间隔生成 72 小时的时隙

Generate 72 hours of timeslots with 15 minutes of interval in android

我正在尝试生成一个间隔为 15 分钟的 72 小时时隙数组,但它在 24 小时后以 00:00 开始,所以基本上它会打印整个 24 小时时隙 3 次,但我想开始来自 00:15..23:45..24:00..24:45..25:00..25:15..72:00

我使用日历 API 的经验较少,

这是我的代码,

        val start_duration = "00:00"
        val end_duration = "72:00"
        val _start_duration = durationFormatter.parse(start_duration)
        val calenderStartDuration = Calendar.getInstance()
        val calenderEndDuration = Calendar.getInstance()
        calenderStartDuration.time = _start_duration
        calenderEndDuration.time = calenderStartDuration.time.addHours(72)
        while (calenderStartDuration.before(calenderEndDuration)){
            calenderStartDuration.add(Calendar.MINUTE, 15)
            val timeStr = durationFormatter.format(calenderStartDuration.time).toLowerCase()
            listBookingDuration.add(timeStr)
        }

使用循环并迭代直到 72 小时(4320 分钟),并编写逻辑以在 15 分钟后获取值

    for (i in 0 until 4321) {
       val remainder = i % 15
       if(remainder==0){
             val hours = i / 60; //since both are ints, you get an int
            val minutes = i % 60;
           listBookingDuration.add(String.format("%02d", hours)+":"+String.format("%02d", minutes))
         }
 }

如果您需要创建适合 72 小时时间跨度的“尽可能多的 15 分钟时段”,从今天午夜开始...那么我将利用 java.time api 的强大功能:

天真pseudo-code,但你明白了:

import java.time.*

fun main() {
        val startTime = LocalTime.of(0, 0)
        val today = LocalDate.now()
        var current = LocalDateTime.of(today, startTime) //use datetime to account for day changes.
        val endDateTime = current.plusHours(72)
        val timeSlots = mutableListOf<LocalTime>()// or LocalDateTime if you need the "date" component as well.
        
        timeSlots.add(current.toLocalTime()) // add the 1st interval
        
        while (current.isBefore(endDateTime)) {
            val newCurrent = current.plusMinutes(15)
            timeSlots.add(newCurrent.toLocalTime()) 
            
            current = newCurrent
        }
        
        println(timeSlots)
}

这会打印:

[00:00, 00:15, 00:30, 00:45, 01:00, 01:15, 01:30, 01:45, 02:00, 02:15, 02:30, 02:45, 03:00, 03:15, 03:30, 03:45, 04:00, 04:15, 04:30, 04:45, 05:00, 05:15, 05:30, 05:45, 06:00, 06:15, 06:30, 06:45, 07:00, 07:15, 07:30, 07:45, 08:00, 08:15, 08:30, 08:45, 09:00, 09:15, 09:30, 09:45, 10:00, 10:15, 10:30, 10:45, 11:00, 11:15, 11:30, 11:45, 12:00, 12:15, 12:30, 12:45, 13:00, 13:15, 13:30, 13:45, 14:00, 14:15, 14:30, 14:45, 15:00, 15:15, 15:30, 15:45, 16:00, 16:15, 16:30, 16:45, 17:00, 17:15, 17:30, 17:45, 18:00, 18:15, 18:30, 18:45, 19:00, 19:15, 19:30, 19:45, 20:00, 20:15, 20:30, 20:45, 21:00, 21:15, 21:30, 21:45, 22:00, 22:15, 22:30, 22:45, 23:00, 23:15, 23:30, 23:45, 00:00, 00:15, 00:30, 00:45, 01:00, 01:15, 01:30, 01:45, 02:00, 02:15, 02:30, 02:45, 03:00, 03:15, 03:30, 03:45, 04:00, 04:15, 04:30, 04:45, 05:00, 05:15, 05:30, 05:45, 06:00, 06:15, 06:30, 06:45, 07:00, 07:15, 07:30, 07:45, 08:00, 08:15, 08:30, 08:45, 09:00, 09:15, 09:30, 09:45, 10:00, 10:15, 10:30, 10:45, 11:00, 11:15, 11:30, 11:45, 12:00, 12:15, 12:30, 12:45, 13:00, 13:15, 13:30, 13:45, 14:00, 14:15, 14:30, 14:45, 15:00, 15:15, 15:30, 15:45, 16:00, 16:15, 16:30, 16:45, 17:00, 17:15, 17:30, 17:45, 18:00, 18:15, 18:30, 18:45, 19:00, 19:15, 19:30, 19:45, 20:00, 20:15, 20:30, 20:45, 21:00, 21:15, 21:30, 21:45, 22:00, 22:15, 22:30, 22:45, 23:00, 23:15, 23:30, 23:45, 00:00, 00:15, 00:30, 00:45, 01:00, 01:15, 01:30, 01:45, 02:00, 02:15, 02:30, 02:45, 03:00, 03:15, 03:30, 03:45, 04:00, 04:15, 04:30, 04:45, 05:00, 05:15, 05:30, 05:45, 06:00, 06:15, 06:30, 06:45, 07:00, 07:15, 07:30, 07:45, 08:00, 08:15, 08:30, 08:45, 09:00, 09:15, 09:30, 09:45, 10:00, 10:15, 10:30, 10:45, 11:00, 11:15, 11:30, 11:45, 12:00, 12:15, 12:30, 12:45, 13:00, 13:15, 13:30, 13:45, 14:00, 14:15, 14:30, 14:45, 15:00, 15:15, 15:30, 15:45, 16:00, 16:15, 16:30, 16:45, 17:00, 17:15, 17:30, 17:45, 18:00, 18:15, 18:30, 18:45, 19:00, 19:15, 19:30, 19:45, 20:00, 20:15, 20:30, 20:45, 21:00, 21:15, 21:30, 21:45, 22:00, 22:15, 22:30, 22:45, 23:00, 23:15, 23:30, 23:45, 00:00]

你可以try and play with this in the Kotlin playground.

现在如果你想让“day2”打印24:00、24:15、24:30、24:45、25:00等,你会可能希望将其保留为 LocalDateTime 并利用日期比较来了解您在序列中的位置;我相信您可以弄清楚这部分,因为您可以很容易地使用 Java.Time api 执行日期算术运算。

请注意,这不是唯一的方法,甚至可能不是最好的方法,但它是 一种 方法。

另一种方法是保持增量并获得 startTime.plus(增量)。 总而言之,Java 时间 API 非常简单。

更新

看来您需要推动才能完成此操作,所以我在操场上花了 15 分钟,想出了一个非常幼稚 的解决方案。剧透警告,没有魔法。

你可以找到 updated playground with this change here 并使用它。

我敢肯定,可能会有很多优化,甚至可能会有更好的方法来实现这一目标,而且功能更强大。希望评论是 self-explanatory.

transform(list) 调用它,你会得到一个 List<String> 打印出来:

[00:00, 00:15 ...omitted for brevity... 24:00, 24:15, 24:30, 24:45, 25:00 ...omitted for brevity... 70:30, 70:45, 71:00, 71:15, 71:30, 71:45, 72:00]

这里是“转换”函数:

fun transform(source: MutableList<LocalDateTime>): List<String> {
        val dayMultiplier = 24 //hours per day, duh!
        val initialDay = source[0].toLocalDate()

        val result = mutableListOf<String>()

        source.forEach {
            val time = it.toLocalTime()
            val hour: Int = time.hour
            
            // calculate the number of days between the dates
            val daysBetween = ChronoUnit.DAYS.between(initialDay, it)
            // Calculate the offset of hours based on the day difference
            val hourOffset = daysBetween * dayMultiplier
            //... and add them to the current hour.
            val newHour = hour + hourOffset

            // Add leading zeros (optional)
            val reformattedHour = if (newHour < 10) "0$newHour" else newHour
            val reformattedMinute = if (time.minute <10) "0${time.minute}" else time.minute
            
            // Naively compose the new time
            val newTime = "$reformattedHour:$reformattedMinute"

            result.add(newTime)
        }

        return result
    }

更新 2

  • 我认为使用 Duration 更好(如 ) by Basil Bourque.
  • 所示
  • 这整个事情可以(并且很可能应该)在同一个循环块中完成。由于您自然会在那里创建对象并将其放入列表中,因此没有什么能阻止您添加添加乘数和直接存储字符串的额外步骤。如果时间轴没有绑定到 date/time 而是时间“间隔”(又名:持续时间),我仍然会尝试存储持续时间。

您保存的数据越完整,就越容易将其“转换”成您需要的任何内容。例如,如果您从 ZonedDateTime 中存储的只是分钟数,那么您将无法从中获取日期……但是如果您保存了整个 ZonedDateTime,您几乎可以从中得到任何东西。

您的问题令人困惑,因为您似乎将 time-of-day 与持续时间值混合在一起。我会照你写的那样去理解。

Duration

使用 Duration 个对象来表示未附加到时间轴的时间跨度。如果不涉及时间线,请不要使用任何date-time 类.

请注意 java.time 类 使用 immutable objects。因此,当增加 15 分钟时,我们会生成一个新的 Duration 对象,而不是改变(“变异”)原始对象。

List < Duration > durations = new ArrayList <>();
Duration increment = Duration.ofMinutes( 15 );
Duration limit = Duration.ofHours( 72 );
Duration duration = Duration.ofMinutes( 15 ); // First starting value.
while ( duration.compareTo( limit ) <= 0 )
{
    durations.add( duration );
    // Set up the next loop.
    duration = duration.plus( increment );
}

System.out.println( "durations = " + durations );

durations = [PT15M, PT30M, PT45M, PT1H, PT1H15M, PT1H30M, PT1H45M, PT2H, PT2H15M, … PT69H, PT69H15M, PT69H30M, PT69H45M, PT70H, PT70H15M, PT70H30M, PT70H45M, PT71H, PT71H15M, PT71H30M, PT71H45M, PT72H]

我强烈建议您 不要 在时钟时间中显示这些值:00:15 到 72:00。这种格式本质上是模棱两可的,很容易被混淆为 time-of-day。相反,如上所示使用 standard ISO 8601 format

但如果你坚持,你可以创建这样的文本。

for ( Duration d : durations )
{
    String text = String.format( "%02d" , d.toHours() ).concat( ":" ).concat( String.format( "%02d" , d.toMinutesPart() ) );
    System.out.println( text );
}
00:15
00:30
00:45
01:00
…
71:00
71:15
71:30
71:45
72:00

如果您真正想要的是在 72 小时内每 15 分钟跟踪一次,知道日期和 time-of-day 这 15 分钟增量中的每一个到达的位置。为此,我将使用 Map、集合 key-value 配对。在您的情况下,键将是一个 Duration 对象,值将是一个 ZonedDateTime 对象,以表示在特定时区中看到的带有 time-of-day 的日期。 Post另一个问题,如果你想走这条路。