[英]SimpleDateFormat timezone bug on Android
我一直試圖在我的應用程序中隔離一個錯誤。 我成功地制作了以下“謎語”:
SimpleDateFormat f1 = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ");
SimpleDateFormat f2 = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ssZ");
Date d = f1.parse("2012-01-01T00:00:00+0700");
String s1 = f1.format(d); // 2011-12-31T18:00:00+0700
String s2 = f2.format(d); // 2011-12-31T18:00:00+0100
當我在Android API 7上運行此代碼時,我在注釋中獲得了值(是的,真的)。 此行為取決於特定的Java實現。
我的問題是:
s2
指向適當的時間點,但s1
卻沒有。 Android的SimpleDateFormat實現似乎存在一個錯誤。 對問題1的回答:請參閱BalusC的答案:
SimpleDateFormat#parse
#parse后]可能需要恢復先前由setTimeZone調用設置的任何TimeZone值以進行進一步操作。 對問題2的回答:請參閱wrygiel的答案(我自己)。
在DateFormat#parse()
javadoc中提到了這一點:
根據給定的解析位置解析日期/時間字符串。 例如,時間文本
"07/10/96 4:5 PM, PDT"
將被解析為等同於Date(837039900000L)
。默認情況下,解析是寬松的:如果輸入不是此對象的格式方法使用的形式,但仍可以解析為日期,則解析成功。 客戶可以通過調用
setLenient(false)
堅持嚴格遵守格式。此解析操作使用
calendar
生成Date
。 因此,calendar's
日期時間字段和TimeZone
值可能已被覆蓋,具體取決於子類實現。 先前通過調用setTimeZone
設置的任何TimeZone
值可能需要恢復以進行進一步操作。
注意最后一段。 遺憾的是,它沒有解釋何時會發生這種情況。 要解決您的特定問題,您需要在格式化操作之前顯式設置所需的時區。
至於SimpleDateFormat
本身的可變性,這已為人所知多年。 您永遠不應該創建它並將其實例指定為靜態或類變量,而應始終作為方法(threadlocal)變量。
這是由於Android 2.1(API 7)中的錯誤造成的。 似乎Android程序員在他們的Android 2.1實現中錯過了一些未記錄的Java行為 (它被歸類為不可修復的bug本身!)。
你的問題引起了我的興趣,所以我繼續編寫你的代碼。 結果? 正如所料......
2011-12-31T18:00:00+0100
2011-12-31T18:00:00+0100
這兩個值是相同的,你使用一些並發? 也許變量在f2.format(d)
之前的另一個線程上被更改。
我嘗試通過運行相同的程序來比較s1和s2。 他們和我一樣。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.