我有一个像" 2d 6:36"这样的字符串,我希望将这个小时数乘以常数。
这意味着我想要计算:
(2*24 + 6 + 36/60) * constant
或者,通常
(d*24 + h + m/60)
任何帮助?
编辑:我只有字符串而不是d,h和m。
答案 0 :(得分:1)
您需要在有用的内容中解析字符串,例如整数列表,您可以使用cl-ppcre:
(defun parse-day-and-time (string)
"Get string like 3d 23:40 and return list (3 23 40)"
(multiple-value-bind (str matches)
(cl-ppcre:scan-to-strings "(\\d+)d ([0-9]|0[0-9]|1[0-9]|2[0-3]):([0-5][0-9])" string)
(declare (ignore str))
(when (< (length matches) 3)
(error "Wrong day and time string: ~A" string))
(map 'list #'parse-integer matches)))
然后你可以做你的计算:
(defun mult-time (string-time coeff)
(destructuring-bind (days hours minutes)
(parse-day-and-time string-time)
(* coeff (+ (* 24 days) hours (/ minutes 60)))))
CL-USER> (mult-time "2d 6:36" 300)
16380
原因如果你想用你的时间做更多的计算,可能最好将它表示为秒数,用它计算,然后用你想要的任何字符串返回它。
答案 1 :(得分:1)
所以我理解数据是人类可读的时间量。例如。 &#34; 2d 1:35&#34;表示2天,1小时35秒或595/12小时。我很想放弃字符串的规范,如下所示:
(defparameter *units* '(("w" . 168) ("d" . 24) (":" . 1)
("h" . 1) ("m" . 1/60) ("s" . 1/3600)))
(defun str-to-hours (str &optional (acc 0))
(or
(cl-ppcre:register-groups-bind (num unit rest)
("(\\d+)\\s*(\\D{0,1})\\D*(.*)" str :sharedp t)
(str-to-hours rest
(+ acc
(* (parse-integer num)
(or (cdr (assoc (string-downcase unit)
*units*
:test #'equal))
1/60)))))
acc))
(str-to-hours "2d 6:36") ; ==> 273/5 ~54.6
(str-to-hours "2D6H36M") ; ==> 273/5 ~54.6
(str-to-hours "2 weeks, 1 day, 3 hours, 7 minutes and 10 seconds") ; ==> 130723/360 ~363.11945
(* 10 (str-to-hours "2d6:36")) ; ==> 546