How to format a duration in java? (e.g format H:MM:SS)

前端 未结 19 1488
情话喂你
情话喂你 2020-11-22 03:32

I\'d like to format a duration in seconds using a pattern like H:MM:SS. The current utilities in java are designed to format a time but not a duration.

相关标签:
19条回答
  • 2020-11-22 04:25

    I didn't see this one so I thought I'd add it:

    Date started=new Date();
    SimpleDateFormat format = new SimpleDateFormat("HH:mm:ss");
    task
    long duration=new Date().getTime()-started.getTime();
    System.out.println(format.format(new Date(duration));
    

    It only works for 24 hours but that's what I usually want for duration.

    0 讨论(0)
  • 2020-11-22 04:27

    Here is one more sample how to format duration. Note that this sample shows both positive and negative duration as positive duration.

    import static java.time.temporal.ChronoUnit.DAYS;
    import static java.time.temporal.ChronoUnit.HOURS;
    import static java.time.temporal.ChronoUnit.MINUTES;
    import static java.time.temporal.ChronoUnit.SECONDS;
    
    import java.time.Duration;
    
    public class DurationSample {
        public static void main(String[] args) {
            //Let's say duration of 2days 3hours 12minutes and 46seconds
            Duration d = Duration.ZERO.plus(2, DAYS).plus(3, HOURS).plus(12, MINUTES).plus(46, SECONDS);
    
            //in case of negative duration
            if(d.isNegative()) d = d.negated();
    
            //format DAYS HOURS MINUTES SECONDS 
            System.out.printf("Total duration is %sdays %shrs %smin %ssec.\n", d.toDays(), d.toHours() % 24, d.toMinutes() % 60, d.getSeconds() % 60);
    
            //or format HOURS MINUTES SECONDS 
            System.out.printf("Or total duration is %shrs %smin %sec.\n", d.toHours(), d.toMinutes() % 60, d.getSeconds() % 60);
    
            //or format MINUTES SECONDS 
            System.out.printf("Or total duration is %smin %ssec.\n", d.toMinutes(), d.getSeconds() % 60);
    
            //or format SECONDS only 
            System.out.printf("Or total duration is %ssec.\n", d.getSeconds());
        }
    }
    
    0 讨论(0)
  • 2020-11-22 04:28

    If you're using a version of Java prior to 8... you can use Joda Time and PeriodFormatter. If you've really got a duration (i.e. an elapsed amount of time, with no reference to a calendar system) then you should probably be using Duration for the most part - you can then call toPeriod (specifying whatever PeriodType you want to reflect whether 25 hours becomes 1 day and 1 hour or not, etc) to get a Period which you can format.

    If you're using Java 8 or later: I'd normally suggest using java.time.Duration to represent the duration. You can then call getSeconds() or the like to obtain an integer for standard string formatting as per bobince's answer if you need to - although you should be careful of the situation where the duration is negative, as you probably want a single negative sign in the output string. So something like:

    public static String formatDuration(Duration duration) {
        long seconds = duration.getSeconds();
        long absSeconds = Math.abs(seconds);
        String positive = String.format(
            "%d:%02d:%02d",
            absSeconds / 3600,
            (absSeconds % 3600) / 60,
            absSeconds % 60);
        return seconds < 0 ? "-" + positive : positive;
    }
    

    Formatting this way is reasonably simple, if annoyingly manual. For parsing it becomes a harder matter in general... You could still use Joda Time even with Java 8 if you want to, of course.

    0 讨论(0)
  • 2020-11-22 04:28

    I use Apache common's DurationFormatUtils like so:

    DurationFormatUtils.formatDuration(millis, "**H:mm:ss**", true);
    
    0 讨论(0)
  • 2020-11-22 04:29

    My library Time4J offers a pattern-based solution (similar to Apache DurationFormatUtils, but more flexible):

    Duration<ClockUnit> duration =
        Duration.of(-573421, ClockUnit.SECONDS) // input in seconds only
        .with(Duration.STD_CLOCK_PERIOD); // performs normalization to h:mm:ss-structure
    String fs = Duration.formatter(ClockUnit.class, "+##h:mm:ss").format(duration);
    System.out.println(fs); // output => -159:17:01
    

    This code demonstrates the capabilities to handle hour overflow and sign handling, see also the API of duration-formatter based on pattern.

    0 讨论(0)
  • 2020-11-22 04:30

    This is easier since Java 9. A Duration still isn’t formattable, but methods for getting the hours, minutes and seconds are added, which makes the task somewhat more straightforward:

        LocalDateTime start = LocalDateTime.of(2019, Month.JANUARY, 17, 15, 24, 12);
        LocalDateTime end = LocalDateTime.of(2019, Month.JANUARY, 18, 15, 43, 33);
        Duration diff = Duration.between(start, end);
        String hms = String.format("%d:%02d:%02d", 
                                    diff.toHours(), 
                                    diff.toMinutesPart(), 
                                    diff.toSecondsPart());
        System.out.println(hms);
    

    The output from this snippet is:

    24:19:21

    0 讨论(0)
提交回复
热议问题