Task

Write a function or program which:

   takes a positive integer representing a duration in seconds as input (e.g., 100), and
   returns a string which shows the same duration decomposed into:
   weeks,
   days, 
   hours, 
   minutes,   and 
   seconds.
This is detailed below (e.g., "2 hr, 59 sec").



Demonstrate that it passes the following three test-cases:

Test Cases


 input number

 output string


 7259

 2 hr, 59 sec


 86400

 1 d


 6000000

 9 wk, 6 d, 10 hr, 40 min

Details
The following five units should be used:



 unit

 suffix used in output

 conversion


 week

 wk

 1 week = 7 days


 day

 d

 1 day = 24 hours


 hour

 hr

 1 hour = 60 minutes


 minute

 min

 1 minute = 60 seconds


 second

 sec



However, only include quantities with non-zero values in the output (e.g., return "1 d" and not "0 wk, 1 d, 0 hr, 0 min, 0 sec").

Give larger units precedence over smaller ones as much as possible (e.g., return 2 min, 10 sec and not 1 min, 70 sec or 130 sec)

Mimic the formatting shown in the test-cases (quantities sorted from largest unit to smallest and separated by comma+space; value and unit of each quantity separated by space).




INCLUDE "H6:REALMATH.ACT"
DEFINE PTR="CARD"
 
TYPE Time=[BYTE s,m,h,d,w]
CARD ARRAY units(5)
 
PROC Convert(REAL POINTER seconds Time POINTER t)
  BYTE ARRAY b,duration=[60 60 24 7]
  BYTE i
  REAL r,n
 
  b=t
  FOR i=0 TO 3
  DO
    IntToReal(duration(i),n)
    RealMod(seconds,n,r)
    b(i)=RealToInt(r)
    RealDivInt(seconds,n,r)
    RealAssign(r,seconds)
  OD
  b(4)=RealToInt(seconds)
RETURN
 
PROC PrintTime(Time POINTER t)
  INT i
  BYTE first,n
  BYTE ARRAY b
 
  b=t i=4 first=1
  WHILE i>=0
  DO
    n=b(i)
    IF n>0 THEN
      IF first=0 THEN
        Print(", ")
      ELSE
        first=0
      FI
      PrintF("%B %S",n,units(i))
    FI
    i==-1
  OD
RETURN
 
PROC Test(CHAR ARRAY s)
  REAL seconds
  Time t
 
  ValR(s,seconds)
  PrintR(seconds) Print(" -> ")
  Convert(seconds,t)
  PrintTime(t) PutE()
RETURN
 
PROC Main()
  Put(125) PutE() ;clear the screen
  MathInit()
  units(0)="sec" units(1)="min"
  units(2)="hr"  units(3)="d"
  units(4)="wk"
  Test("7259")
  Test("86400")
  Test("6000000")
RETURN
 