【问题标题】:Value 24 for hourOfDay must be in the range [0,23]hourOfDay 的值 24 必须在 [0,23] 范围内
【发布时间】:2021-01-08 08:19:07
【问题描述】:

我在我的 Android 应用程序中使用了一个 REST 服务,它给了我一个时间,只是时间,但它也会返回类似的东西

"24:38:00""25:15:00"

所以,我需要的是解析这次并以 24 小时格式输出真实结果。应该是

"00:38:00""01:15:00"

我试过用这种方式

LocalTime localTime = new LocalTime(timeModel.getTimeString());

但我现在有这个错误Cannot parse "24:38:00": Value 24 for hourOfDay must be in the range [0,23]

我该如何解决?我只需要时间而不是日期

【问题讨论】:

  • 怎么样.. 如果小时 >= 24,减去 24?
  • @ShioT 你认为这是最好的方法吗?你能告诉我你的意思吗?
  • hourOfDay % 24?

标签: java android time java-time localtime


【解决方案1】:

你真的应该修复这个服务器。如果这是不可能的,你将不得不使用类似的东西来解决这个错误

String fixServerTime(String time) {
  if (time.startsWith("24")) {
    return "00" + time.substring(2)
  } else {
    return time
  }
)

// elsewhere
LocalTime localTime = new LocalTime(fixServerTime(timeModel.getTimeString()));

【讨论】:

  • 有时看起来这样是有原因的。据我所知,日本的深夜电视节目表超过 24 点,所以他们说的不是“周三凌晨 3 点”,而是“周二 27 点”。
  • 这个答案不适合超过 25 小时的小时数,但 OP 可能会接受这个想法并稍微调整一下。
  • 嗯,ISO 标准只允许 0-23,java.time API 是基于该标准的,所以要在这种“自定义”环境中成功使用它们,就必须“破解”:)
【解决方案2】:

在这种情况下,您可以假设这些时间字符串不遵循任何规则,因为如果 2425 作为“小时”部分的值存在,他们为什么不回复 37

你可以用它来清理它:

private static String modifyTimeString(String s) {
  //the hour might only be 1 digit, so "the first 2 chars" is not a safe approach
  int colonIndex = s.indexOf(':');
  String hoursString = s.substring(0, colonIndex);
  Integer hours = Integer.valueOf(hoursString);
  if(hours < 24) {
    return s;
  }
  /*while(hours >= 24) {
    hours -= 24;
  }*/
  //smarter, see ronos answer:
  hours = hours % 24;
  //put a leading 0 in there for single-digit-hours
  hoursString = hours.toString();
  if(hours<10) {
    hoursString = "0" + hoursString;
  }
  return hoursString + s.substring(colonIndex);
}

调用modifyTimeString("25:15:00") 返回"01:15:00"

【讨论】:

  • 我试过这个,效果很好。当然,服务器有问题。但我无法修复它。这种方法是一个很好的解决方法。谢谢
【解决方案3】:

你可以拆分时间字符串得到小时、分钟、秒然后使用LocalTime.of

String timeData = "25:15:00";
String[] timeParts = timeData.split(":");
LocalTime localTime = LocalTime.of(Integer.parseInt(timeParts[0]) % 24,
                                   Integer.parseInt(timeParts[1]), 
                                   Integer.parseInt(timeParts[2]));

【讨论】:

  • 我不会真的相信输入值总是为“小时”部分提供 2 位数字...
  • 当他们滥用小时,为什么不滥用分钟和秒呢?当您同时使用 % 60 来表示分钟和秒时,这可能是最强大的
【解决方案4】:

使用宽松的解析器

您需要的是一个用于解析的宽松格式化程序——或者更准确地说,一个具有宽松解析器样式的格式化程序(格式化程序也有一个解析样式,在您的情况下它不需要是宽松的)。

    DateTimeFormatter timeFormatter = DateTimeFormatter.ISO_LOCAL_TIME
            .withResolverStyle(ResolverStyle.LENIENT);
    String timeString = "25:15:00";
    
    LocalTime time = LocalTime.parse(timeString, timeFormatter);
    System.out.println(time);

输出:

01:15

您不需要任何手动解析,也不需要任何if 语句,也不需要任何模运算。您不需要处理任何特殊情况。您可以将其全部留给标准库。这对可读性和对代码的信任都有好处。

【讨论】:

  • 哇!这是本页所有答案中最好的!
猜你喜欢
  • 2023-03-16
  • 1970-01-01
  • 1970-01-01
  • 2018-02-22
  • 2020-06-24
  • 1970-01-01
  • 2020-09-11
  • 2023-01-21
  • 2012-07-20
相关资源
最近更新 更多