一、簡介
過年是中國(以及日本、韓國等國)人民的第一大節日。你怎麼知道哪天過年?查日曆或者聽別人說?程式員當然有程式員的辦法,就是寫程式啦。
雖然西曆(俗稱的“陽曆”)已經成了全世界的通用標準,而且也具有多方面的優越性。但在東亞地區,還是離不開“農曆”,春節、元宵、端午、中秋、重陽這些節日是農曆的,大部份人的老爸老媽的生日也是農曆的。
早在1.0架構出來的時候,我就認為微軟公司不應該“厚彼薄此”,在.net架構中提供了希伯來曆等,卻沒有提供更廣泛使用的“農曆”。
而在.net 2.0中,微軟公司終於做出了這個小小的改進。
.net 2.0在System.Globalization命名空間中新增加了EastAsianLunisolarCalendar 類及以繼承它的ChineseLunisolarCalendar, JapaneseLunisolarCalendar, KoreanLunisolarCalendar, TaiwanLunisolarCalendar等幾個類。LunisolarCalendar顧名思義應為“陰陽曆”,我的理解是因為我們所用的農曆雖然按照月亮公轉來編月份,但用“閏月”的方式來調整年份與地球公轉的誤差,嚴格意義上來說是結合了月亮公轉和地球公轉的成份,因此屬於“陰陽曆”。但我這裡還是按照習慣稱之為“農曆” 。
二、新的農曆類還是沒有公民待遇
為了測試新的日曆類,我興沖沖地寫了幾句代碼:(省略了調用這個方法的其它代碼)
private string getDateString(DateTime dt)
{
CultureInfo ci = new CultureInfo("zh-CN");
ci.DateTimeFormat.Calendar = new ChineseLunisolarCalendar();
return dt.ToString("D",ci);
}
運行報錯,錯誤資訊是:"Not a valid calendar for the given culture "
為了說明問題,繼續測試
private string getDateString(DateTime dt)
{
CultureInfo ci = new CultureInfo("zh-TW");
ci.DateTimeFormat.Calendar = new TaiwanCalendar();
return dt.ToString("D",ci);
}
可以正常運行,結果是95年x月x日(民國紀年),注釋掉中間那條語句,結果是2006年x月x日(也就是使用西曆),將中間那條語句修改成:ci.DateTimeFormat.Calendar = new TaiwanLunisolarCalendar(),照樣出錯。查相關資料,原來DateTimeFormat的Calendar屬性只能為CultureInfo的OptionalCalendars屬性所指定範圍。
於是再寫一段代碼測試OptionalCalendars的內容,對於zh-CN語言,惟一可用於日期格式的calendar是本地化的GregorianCalendar(也就是西曆)。對於zh-TW,可用於日期格式的calendar是美國英語和本地化的GregorianCalendar以及TaiwanCalendar(即西曆的年份減1911),都沒有包括農曆。
也就是說.net2.0雖然提供了農曆類,但對它的支援並不及同樣有閏月的希伯來曆。我查資料的時候找到了部落格堂的一篇文章http://blog.joycode.com/percyboy/archive/2004/09/17.aspx ,作者在一年半以前發現了農曆類不支援日期格式化的問題,並認為這是一個bug。當然還算不上bug,只不過微軟沒有重視而已(責任在微軟嗎?我想應該不是,在商業社會我們有多重視微軟就會有多重視。和以色列比起來,我們對傳統文化的重視程度差得太遠)。