newLISP 簡介/日期和時間操作
要操作日期和時間,請使用以下函式:
- date 將秒數轉換為日期/時間,或返回當前日期/時間
- date-value 返回自 1970-1-1 以來某個日期和時間的秒數,或者返回當前時間
- now 在一個列表中返回當前日期/時間資訊
- time-of-day 返回自今日開始至今的毫秒數
date-value 和 now 工作在 UT 中,而不是您的本地時間。date 可以考慮您的本地時間與 UT 之間的時間差。
所有四個函式都可以用來返回當前時間的資訊。date-value 返回 1970 年與當前時間(UT)之間的秒數
1142798985
而 now 返回一個包含當前日期和時間資訊(UT)的整數列表
(now)
;-> (2006 3 19 20 5 2 125475 78 1 0 0)
這提供了以下資訊:
- 年、月、日 (2006, 3, 19)
- 時、分、秒、微秒 (20, 5, 2, 125475)
- 當前年份中的日期 (78)
- 當前星期中的日期 (1)
- 本地時區偏移量(以分鐘計,西經 GMT)(0)
- 夏令時標誌 (0)
要提取您想要的資訊,請使用切片或挑選出元素
(slice (now) 0 3) ; year month day using explicit slice
(0 3 (now)) ; year month day using implicit slice
(select (now) '(0 1 2)) ; year month day using selection
(3 3 (now)) ; hour minute second
(nth 8 (now)) ; day of the week, starting from Sunday
date 單獨使用將為您提供本地時區的當前日期和時間(now 和 date-value 返回的是 UCT/UTC 值,而不是相對於您的本地時區)
(date)
;-> "Mon Mar 19 20:05:02 2006"
它還可以告訴您自 1970 年(Unix 紀元開始)以來的某個整數秒數的日期,並根據您的本地時區進行調整
(date 0) ; a US newLISP user sees this
;-> "Wed Dec 31 16:00:00 1969"
(date 0) ; a European newLISP user sees this
;-> "Thu Jan 1 01:00:00 1970"
date-value 可以計算特定日期或日期/時間(UT)的秒數
(date-value 2006 5 11) ; just the date
;-> 1147305600
(date-value 2006 5 11 23 59 59) ; date and time (in UT)
;-> 1147391999
因為 date-value 可以接受年、月、日、時、分和秒作為輸入,所以它可以應用於 now 的輸出
(apply date-value (now))
;-> 1164723787
透過將不同的時間轉換為這些日期值,您可以進行計算。例如,要從 2005 年 1 月 3 日減去 2003 年 11 月 13 日
(- (date-value 2005 1 3) (date-value 2003 11 13))
;-> 36028800
; seconds, which is
(/ 36028800 (* 24 60 60))
;-> 417
; this is a duration in days - don't convert this to a date!
您可以透過將 12 天的秒數加到該日期來找出 2005 年聖誕節後的第 12 天的日期
(+ (date-value 2005 12 25) (* 12 24 60 60))
; seconds in 12 days
;-> 1136505600
; this is an instant in time, so it can be converted!
這個秒數值可以透過 date 以更長的形式轉換為人們可以理解的日期,當它接受一個自 1970 年以來的秒數值,並將它轉換為基於 UT 值的本地時區表示
(date 1136505600)
;-> "Fri Jan 6 00:00:00 2006" ; for this European user...
當然 (date (date-value)) 與 (date) 相同,但如果您想更改日期格式,則必須使用更長的形式。date 接受一個額外的格式字串(以分鐘為單位的時間偏移量為字首)。如果您熟悉 C 語言風格的 strftime 格式,您將知道該怎麼做
(date (date-value) 0 "%Y-%m-%d %H:%M:%S") ; ISO 8601
;-> 2006-06-08 11:55:08
(date 1136505600 0 "%Y-%m-%d %H:%M:%S")
;-> "2006-01-06 00:00:00"
(date (date-value) 0 "%Y%m%d-%H%M%S") ; in London
;-> "20061207-144445"
(date (date-value) (* -8 60) "%Y%m%d-%H%M%S") ; in Los Angeles
;-> "20061207-064445" ; 8 hours offset
parse-date 函式(不幸的是,在 Windows 上不可用)可以將日期和時間字串轉換為自 1970 年以來的秒數值。您在字串之後提供一個日期時間格式字串
(parse-date "2006-12-13" "%Y-%m-%d")
;-> 1165968000
(date (parse-date "2007-02-08 20:12" "%Y-%m-%d %H:%M"))
;-> "Thu Feb 8 20:12:00 2007"
為了計時,您可以使用以下函式:
- time 返回評估表示式所花費的時間,以毫秒為單位
- timer 設定一個計時器,等待一定秒數,然後評估表示式
- sleep 停止工作一定毫秒數
time 有助於找出表示式評估花費的時間
(time (read-file "/Users/me/Music/iTunes/iTunes Music Library.xml"))
;-> 27 ; milliseconds
您也可以提供重複次數,這可能會提供更準確的結果
(time (for (x 1 1000) (factor x)) 100) ; 100 repetitions
;-> 426
如果您不能或不想包含表示式,則可以使用 time-of-day 進行更簡單的計時
(set 'start-time (time-of-day))
(for (i 1 1000000)
(set 'temp (sqrt i)))
(string {that took } (div (- (time-of-day) start-time) 1000) { seconds})
;-> "that took 0.238 seconds"
timer 本質上是一個鬧鐘。設定它,然後直到時間到來就不用管它。您提供一個指定警報操作的符號,然後是等待的秒數
(define (teas-brewed)
(println (date) " Your tea has brewed, sir!"))
(timer teas-brewed (* 3 60))
三分鐘後,您將看到以下內容:
Sun Mar 19 23:36:33 2006 Your tea has brewed, sir!
如果沒有引數,此函式將返回已分配為警報操作的當前符號的名稱
(timer)
;-> teas-brewed
如果您正在等待警報響起,並且您迫不及待地想知道到目前為止已經過去了多少時間,請使用帶分配符號名稱但沒有秒數值的函式
(timer teas-brewed)
;-> 89.135747
; waited only a minute and a bit so far
有關這些函式用法的另一個示例,請參閱 簡單倒計時器。