How to parse HH: mm into the number of minutes, taking into account the locale's time separator?

I have an input string of the format "HH: mm" where the time separator matches the language setting (for example, "10: 45" for USA or "10.45" for Italy). I need to convert it to a number of minutes.

This is what I came up with:

String timeSeparator = getTimeSeparator(locale);
String[] duration = durationString.split(Pattern.quote(timeSeparator));
int minutes = Integer.valueOf(duration[0])*60 + Integer.valueOf(duration[1]);

      

getTimeSeparator

method taken from stackoverflow question/1043525 / ...

Is there an easier way? For example using `java.time '.

+3


source to share


5 answers


In Java 8 you can use DateTimeFormatter.ofLocalizedTime

to get the date and time format. Then you can use it to parse the string intoLocalTime

and extract the minute field .

public static int getMinute(String timeString, Locale locale) {
  DateTimeFormatter formatter = DateTimeFormatter.ofLocalizedTime(FormatStyle.SHORT)
                                                 .withLocale(locale);
  LocalTime time = LocalTime.parse(timeString, formatter);
  return time.getHour()*60 + time.getMinute();
}

      

Example:

System.out.println(getMinute("10.47", new Locale("fi")));   // 647
System.out.println(getMinute("11:23", Locale.ROOT));        // 683

      




If you don't need a time separator, we could use a fixed pattern.

public static int getMinute(String timeString, Locale locale) {
  DateTimeFormatter formatter = DateTimeFormatter.ofPattern("HH[:][.]mm", locale);
  LocalTime time = LocalTime.parse(timeString, formatter);
  return time.getHour()*60 + time.getMinute();
}

      

( […]

Is optional, so it will fit HH:mm

, HH.mm

, HHmm

and HH:.mm

)

+1


source


TL; DR

Duration.parse( 
    "PT" + 
    "10:45".replace( ":" , "M" )
           .replace( "-" , "M" )
           .replace( "." , "M" )
           .replace( "," , "M" )
    + "S" 
).toMinutes()

      

"10:45" → PT10M45S → 10

ISO 8601 format

The ISO 8601 standard defines the format for such time intervals that are not tied to the timeline:PnYnMnDTnHnMnS

The icon P

indicates the beginning. T

separates any years-months-days from hours-minutes-seconds. So, an hour and a half - PT1H30M

. Your example is ten minutes and forty-five seconds PT10M45S

.

Perform simple string manipulation to convert your input to this format.

String input = "10:45" ;
String inputStandardized = "PT" + 
    input.replace( ":" , "M" )
         .replace( "-" , "M" )
         .replace( "." , "M" )
         .replace( "," , "M" )
         + "S" ;

      

PT10M45S



Duration

Disassemble how Duration

. The java.time classes use ISO 8601 formats by default when parsing and generating strings. Therefore, there is no need to specify a formatting template.

Duration duration = Duration.parse( inputStandardized );

      

duration.toString (): PT10M45S

You can use an object Duration

to do date and time math by going to plus

and minus

. Thus, you may not need the minutes as an integer. But you can set the total number of minutes in the duration.

long minutes = duration.toMinutes();

      

ten

See this code run at IdeOne.com .

Council. Using the clock format over a period of time is problematic. Ambiguity leads to confusion and errors. I suggest using the ISO 8601 standard formats for durations as they are designed to be unambiguous, easy to read, and easy to parse.

+1


source


Notice very elegant, but it will get the job done

String pattern = DateTimeFormatter.ofLocalizedTime(FormatStyle.SHORT)
    .withLocale(locale).format(LocalTime.MIN)
    .replaceFirst("\\d*", "H").replaceFirst("\\d.*", "mm");
DateTimeFormatter formatter = DateTimeFormatter.ofPattern(pattern, locale);
int minutes = formatter.parse(string).get(ChronoField.MINUTE_OF_DAY);

      

+1


source


You can use the method getLocalizedDateTimePattern

to get a template with which to initialize DateTimeFormatter

to parse the time with a given language. The first one null

refers to a date that you don't need in your case.

String timePattern = DateTimeFormatterBuilder.getLocalizedDateTimePattern(
            null, FormatStyle.SHORT, IsoChronology.INSTANCE, locale);

      

Then you use it to create the formatting (note that you need to specify the locale again):

DateTimeFormatter dtf = DateTimeFormatter.ofPattern(timePattern, locale);

      

If, instead of formatting SHORT

for, locale

you expect "HHcmm"

where 'c'

is a non-numeric char that is the time separator for that locale

, then either:

  • extract numbers from text

    String[] duration = durationString.split("\\D");
    int minutes = parseInt(duration[0])*60 + parseInt(duration[1]);
    
          

  • do DateTimeFormatter

    with time separator

    DateTimeFormatter dtf = DateTimeFormatter.ofPattern(
            String.format("HH%smm", timeSeparator), locale);
    LocalTime time = LocalTime.parse(text, dtf);
    int minutes = time.toSecondOfDay() / 60;
    
          

    or if you should

    int minutes = ChronoUnit.MINUTES.between(LocalTime.MIN, time);
    
          

0


source


First analyze the time of the instance LocalTime

, then calculate the difference at the start of the day with Duration

:

    DateTimeFormatter formatter = new DateTimeFormatterBuilder()
            .appendLocalized(null, FormatStyle.SHORT)
            .toFormatter(Locale.ITALY);
    LocalTime time = LocalTime.from(formatter.parse("10.45"));
    long minutes = Duration.between(LocalTime.MIN, time).toMinutes();

      

higher results up to 645

0


source







All Articles