[英]bash script looping through dates gets stuck?
我正在使用下面的 bash 腳本來啟動一個 python 程序。 它完全按照我的預期循環遍歷日期/時間。 但是,然后,它被困在“2018-11-04 01:45:00”。 將 15 分鍾添加到“2018-11-04 01:45:00”返回“2018-11-04 01:00:00”,而不是“2018-11-04 02:00:00”。 有沒有人經歷過這個?
#!/bin/bash
dEND=$(date +"%F %T" -d "2020-03-15 00:00:00")
dCUR=$(date +"%F %T" -d "2018-11-04 01:00:00")
echo $dCUR $dEND
typeset -i sEND=1
typeset -i sCUR=0
echo $sCUR $sEND
while( (( $sCUR < $sEND )) );do
dCUR=$(date +"%F %T" -d "$dCUR 15 minutes")
typeset -i sEND=$(date +%s -d "$dEND")
typeset -i sCUR=$(date +%s -d "$dCUR")
echo $dCUR $dEND $sCUR
done
echo done
$ dCUR=$(date +"%F %T" -d "2018-11-04 00:00:00")
$ echo $dCUR
2018-11-04 00:00:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 00:15:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 00:30:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 00:45:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 01:00:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 01:15:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 01:30:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 01:45:00
$ dCUR=$(date +"%F %T" -d "$dCUR 15 minutes");echo $dCUR
2018-11-04 01:00:00
我懷疑您(或更准確地說,您的機器)可能位於(或更准確地說,配置為好像它位於)巴哈馬、百慕大、巴西、加拿大、古巴、斐濟、格陵蘭、海地、墨西哥、聖皮埃爾密克隆、特克斯和凱科斯群島以及美國。
我不能確定,因為您的個人資料沒有關於您所在位置的信息,但我很想知道我離現實有多近。
你的代碼在我的系統上運行良好,但我的地理區域不做夏令時。
在許多地方,這種轉換往往發生在凌晨 2 點到 3 點左右,因此它可能只是您選擇的日期的產物。 從這里的這個頁面來看,似乎有幾個地方確實在 11 月 4 日進行了切換(因此我在此答案的第一段中列出了位置列表)。
您可以通過運行完全相同的實驗來確認這一點,但使用 11 月 5 日而不是您選擇的日期。 您還可以添加%z
格式說明符,您應該會看到它從(例如) +08
更改為+07
。
與世界時間的大多數問題一樣,最好的解決方案是盡快將所有本地時間轉換為 UTC,並盡可能晚地將它們轉換回本地時間。 這樣,除了與最終用戶(通常以當地時間考慮)進行交互的地方,您大多擁有一致的時基。
例如,這里有一個從凌晨 1 點到凌晨 5 點運行的腳本,在該范圍內有一個時區切換的區域。
#!/bin/bash
# My region doesn't do DST but New York does, so fake it.
export TZ=America/New_York
# Helper functions for UTC/local conversion.
utcFmt="%F %T %z"
localFmt="%F %T"
utcToLocal() {
echo "$(date +"${localFmt}" -d "$(date +"${utcFmt}" -d "$1")")"
}
localToUtc() {
echo "$(date -u +"${utcFmt}" -d "$(date +"${utcFmt}" -d "$1")")"
}
# Init UTC values based on local time.
utcCur="$(localToUtc "2018-11-04 01:00:00")"
utcEnd="$(localToUtc "2018-11-04 05:00:00")"
echo "Going from ${utcCur} to ${utcEnd}"
while [[ "${utcCur}" < "${utcEnd}" ]] ; do
# Display local time, but adjust UTC time.
echo "At $(utcToLocal "${utcCur}")"
utcCur="$(date -u +"${utcFmt}" -d "$utcCur 15 minutes")"
done
正如您從輸出中看到的那樣,有一個回滾到更早的時間,因為這就是您將時鍾倒轉時會發生的情況(請參閱*
標記):
Going from 2018-11-04 01:00:00 to 2018-11-04 05:00:00
At 2018-11-04 01:00:00
At 2018-11-04 01:15:00
At 2018-11-04 01:30:00
At 2018-11-04 01:45:00
At 2018-11-04 01:00:00 * Roll back one hour (once).
At 2018-11-04 01:15:00
At 2018-11-04 01:30:00
At 2018-11-04 01:45:00
At 2018-11-04 02:00:00 * Keep going.
At 2018-11-04 02:15:00
At 2018-11-04 02:30:00
At 2018-11-04 02:45:00
At 2018-11-04 03:00:00
At 2018-11-04 03:15:00
At 2018-11-04 03:30:00
At 2018-11-04 03:45:00
At 2018-11-04 04:00:00
At 2018-11-04 04:15:00
At 2018-11-04 04:30:00
At 2018-11-04 04:45:00
而且,如果您轉到夏令時的另一端(一個小時消失的地方),您也可以看到(再次注意*
標記):
utcCur="$(localToUtc "2018-03-11 01:00:00")"
utcEnd="$(localToUtc "2018-03-11 05:00:00")"
Going from 2018-03-11 01:00:00 to 2018-03-11 05:00:00
At 2018-03-11 01:00:00
At 2018-03-11 01:15:00
At 2018-03-11 01:30:00
At 2018-03-11 01:45:00
At 2018-03-11 03:00:00 * Put clock foward one hour.
At 2018-03-11 03:15:00
At 2018-03-11 03:30:00
At 2018-03-11 03:45:00
At 2018-03-11 04:00:00
At 2018-03-11 04:15:00
At 2018-03-11 04:30:00
At 2018-03-11 04:45:00
2018-11-04 是十一月的第一個星期天。 在夏令時和標准時間之間切換的北美地區和附近地區目前在 11 月的第一個星期日(以及其他過渡的 3 月的第二個星期日)進行。 這意味着在 11 月,時間從 01:59:59 xDT 到 01:00:00 xST(春天向前;后退)。 添加和結果是正確的——即使它不是你所期望的。
歐洲的地方目前在 3 月的最后一個星期天向前轉換,在 10 月的最后一個星期日回落,因此比美國的變化在春季晚 2 或 3 周,在秋季早 1 周。 如果 3 月 1 日是周一至周四,則間隔為 2 周; 周五至周日,3 周。
其他國家仍然有不同的規則,有時會受到農歷和宗教觀察的影響。
GNU 日期格式字符串非常靈活,但從長遠來看是不可靠的。
要執行您想要的操作,請將日期轉換為自紀元以來的秒數,添加15*60
秒,然后轉換回您想要的格式。
那將是:
dCUR=$(date -d "@$(($(date --date="$dCUR" +%s) + 15 * 60))" +"%F %T"); echo $dCUR
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.