2011-05-25 40 views
2

我處於一種情況,即我的程序有2個對第三方系統的集成。該集成包括1)TCP/IP上的XML協議和2)WCF中的Web服務。DateTime必須包含TimeZone信息並將夏令時考慮在內

在任何一種情況下,集成合作夥伴都需要傳遞給他們的時間戳/日期時間以包含有關時區和夏令時的信息,以便他們可以顯示正確的時間,而不管其客戶的時區/位置。

我寧願不更改當前的協議,在任何情況下他們都期望DateTime,所以我的問題是:是否可以將TimeZone和夏令時信息作爲DateTime的一部分傳遞?

現在我的時間戳看起來是這樣的:

2011-04-27T15:14:13.963 

我很想有它看起來像這樣(我設在丹麥,所以我們使用CEST),並能夠將信息與傳遞DateTime對象

2011-04-27T15:14:13.963 +01:00 

但是我不知道我應該如何做到這一點,也沒有考慮到夏令因子

+0

'DateTime'是古代科技。去參加最近的.NET考試。 :) – bzlm 2011-05-25 11:33:02

+1

DateTimeOffset.Now.ToString(「yyyy-mm-ddTHH:MM:ss zzz」); – 2011-05-25 12:04:21

回答

2

使用UTC時間,你可以堅持使用DateTime。 UTC在原地轉換爲本地(或任何其他時間)。這也解決了夏令時問題。使用UTC是最好的解決方案,我對它有一些瞭解。

小演示:

namespace TimeZoneTest 
{ 
    using System; 
    using System.Globalization; 

    class Program 
    { 
     static void Main(string[] args) 
     { 
      // get local time 
      DateTime localTime = DateTime.Now; 
      Console.WriteLine(string.Format(
       CultureInfo.CurrentCulture, 
       "localTime = {0}, localTime.Kind = {1}", 
       localTime, 
       localTime.Kind)); 

      // get local time zone, or use TimeZoneInfo to get any time zone you want 
      TimeZone ltz = TimeZone.CurrentTimeZone; 
      Console.WriteLine(string.Format("local time zone = {0}", ltz.StandardName)); 

      // convert local time to UTC 
      DateTime utcTime = ltz.ToUniversalTime(localTime); 
      Console.WriteLine(string.Format(CultureInfo.CurrentCulture, 
       "utcTime = {0}, utcTime.Kind = {1}", 
       utcTime, 
       utcTime.Kind)); 

      // transfer date via service, as ISO time string 
      string isoUtc = utcTime.ToString("o"); 
      Console.WriteLine("..."); 
      Console.WriteLine(string.Format("transfer: isoUtc = {0}", isoUtc)); 
      Console.WriteLine("..."); 

      // now on the other side 
      DateTime utcTimeRecieved = DateTime.ParseExact(
       isoUtc, 
       "o", 
       CultureInfo.InvariantCulture, 
       DateTimeStyles.RoundtripKind); 
      Console.WriteLine(string.Format(CultureInfo.CurrentCulture, 
       "utcTimeRecieved = {0}, utcTimeRecieved.Kind = {1}", 
       utcTimeRecieved, 
       utcTimeRecieved.Kind)); 

      // client time zone, or use TimeZoneInfo to get any time zone you want 
      TimeZone ctz = TimeZone.CurrentTimeZone; 
      Console.WriteLine(string.Format("client time zone = {0}", ctz.StandardName)); 

      // get local time from utc 
      DateTime clientLocal = ctz.ToLocalTime(utcTimeRecieved); 
      Console.WriteLine(string.Format(
       CultureInfo.CurrentCulture, 
       "clientLocal = {0}, clientLocal.Kind = {1}", 
       clientLocal, 
       clientLocal.Kind)); 

      Console.WriteLine("\nPress any key to exit.."); 
      Console.ReadKey(); 
     } 
    } 

}

+0

你能舉出一個例子嗎? – Memphis 2011-05-25 12:23:55

+0

增加了演示代碼來回答。 – 2011-05-25 17:19:04

3

而不是DateTime使用DateTimeOffset,其中包含時區偏移量信息。

至於夏令時 - 您將需要使用Olsen database

請參閱this相關問題。

+1

DateTimeOffset *不包含時區信息。它包含* offset *信息,這是不一樣的。 – 2011-05-25 11:47:51

+0

@Jon - 感謝您的糾正。 – Oded 2011-05-25 11:56:15

+0

Congratz on 100k Oded :-) – BrokenGlass 2011-05-25 12:50:55

5

如果你需要知道,這兩個日期/時間時區,你就必須拿出自己的封裝:

  • DateTime只包含日期/時間和信息,以無論是「本地」(在系統時區)或UTC
  • DateTimeOffset包含有關的日期/時間和UTC標準信息,但是這是不一樣的時區

你ç在結構中應該合併TimeZoneInfoDateTimeOffset

或者,如果你樂於使用的β-質量,API-能,仍然改變軟件,你可以使用Noda Time,我在一個項目開始基本端口Joda Time API到.NET。

這就是在進程中的表示......至於傳遞信息,你需要找出你的集成合作夥伴使用什麼。例如,他們可能希望UTC時間和一個奧爾森時區名稱......或者他們可能只是想要的偏移量。

如果您只需要知道在創建時間戳時用戶的本地時間是什麼,那麼包括來自UTC 的「當前」偏移量可能是就足夠了,而不包括全部時區信息。這只是意味着你不知道2秒後當地時間是什麼......

+0

那麼你基本上說的是,我沒有辦法將DateTime和TimeZone內的信息都傳遞給DateTime對象? 我需要一個結構或一個自定義類來包含一個對象內的信息。 – Memphis 2011-05-25 11:55:10

+0

@Memphis:號碼。「DateTime」只知道其餘信息是「本地」還是「UTC」(或未指定)。 – 2011-05-25 11:55:54

+0

你也可以舉一個簡單的例子,將TimeZoneInfo和DateTimeOffset與另一個結合使用。 我從數據庫JIT fyi中檢索我的時間戳。 – Memphis 2011-05-25 12:00:23

相關問題