[转]使用C#获取当前Windows所设定的时区

文章围绕2ndgatechina的笔试project,介绍编写.NET API实现任意时区时间与当前时间相互转换。过程中提及获取系统当前时区需用kernel32.dll中的GetTimeZoneInformation系统API,还说明了获取windows设定的全部时区信息的方法,最终可实现windows提供时区间的任意转换。

2ndgatechina的笔试project:写一个.NET API,能使其他devs能够调用他来将任意时区的时间转换为当前时间或者将当前时间转换为任意时区的时间。

咋一看,好像比较简单,真做的时候才发现我怎么去获取我系统的当前时区呢?上http://www.pinvoke.net上查,发现需要使用kernel32.dll中的GetTimeZoneInformation的系统API。

现成的例子参看这里,我就不详细说了:http://www.pinvoke.net/default.aspx/kernel32.GetTimeZoneInformation

在这个基础上我们来扩展一下:如何去取得windows所给我们设定的全部时区呢?

其实windows所设定的时区全部保存在 \KEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Time Zones的目录里,那么很自然我们有代码:

1 None.gif  RegistryKey key  =                                Registry.LocalMachine.OpenSubKey( 
2 None.gif                                     @" SOFTWARE\Microsoft\Windows NT\CurrentVersion\Time Zones "  ) )
3 ExpandedBlockStart.gifContractedBlock.gif                         dot.gif {
4InBlock.gif                            string[] zoneNames = key.GetSubKeyNames();
5InBlock.gif
6InBlock.gif                            foreach ( string zoneName in zoneNames )
7ExpandedSubBlockStart.gifContractedSubBlock.gif                            dot.gif{
8InBlock.gif                                using ( RegistryKey subKey = key.OpenSubKey( zoneName ) )

等等,这里的TZI是二进制的,这种又代表什么呢?仍然是上面的pinvoke的链接,可以将这些二进制数据转换为里面所定义的结构体。那么可以通过如下方法枚举出Time Zones的所有子键信息:

 1 None.gif public   static  TimeZoneInformation[] EnumZones()
 2 ExpandedBlockStart.gifContractedBlock.gif         dot.gif {
 3InBlock.gif            if ( s_zones == null )
 4ExpandedSubBlockStart.gifContractedSubBlock.gif            dot.gif{
 5InBlock.gif                lock( s_lockZones )
 6ExpandedSubBlockStart.gifContractedSubBlock.gif                dot.gif{
 7InBlock.gif                    if ( s_zones == null )
 8ExpandedSubBlockStart.gifContractedSubBlock.gif                    dot.gif{
 9InBlock.gif                        ArrayList zones = new ArrayList();
10InBlock.gif
11InBlock.gif                        using ( RegistryKey key = 
12InBlock.gif                                    Registry.LocalMachine.OpenSubKey( 
13InBlock.gif                                    @"SOFTWARE\Microsoft\Windows NT\CurrentVersion\Time Zones" ) )
14ExpandedSubBlockStart.gifContractedSubBlock.gif                        dot.gif{
15InBlock.gif                            string[] zoneNames = key.GetSubKeyNames();
16InBlock.gif
17InBlock.gif                            foreach ( string zoneName in zoneNames )
18ExpandedSubBlockStart.gifContractedSubBlock.gif                            dot.gif{
19InBlock.gif                                using ( RegistryKey subKey = key.OpenSubKey( zoneName ) )
20ExpandedSubBlockStart.gifContractedSubBlock.gif                                dot.gif{
21InBlock.gif                                    TimeZoneInformation tzi = new TimeZoneInformation();
22InBlock.gif                                    tzi.m_name = zoneName;
23InBlock.gif                                    tzi.m_displayName = (string) subKey.GetValue( "Display" );
24InBlock.gif                                    tzi.m_standardName = (string) subKey.GetValue( "Std" );
25InBlock.gif                                    tzi.m_daylightName = (string) subKey.GetValue( "Dlt" );
26InBlock.gif                                    tzi.m_index = (int)( subKey.GetValue( "Index" ) );
27InBlock.gif
28InBlock.gif                                    tzi.InitTzi( (byte[]) subKey.GetValue( "Tzi" ) );
29InBlock.gif                            
30InBlock.gif                                    zones.Add( tzi );
31ExpandedSubBlockEnd.gif                                }

32ExpandedSubBlockEnd.gif                            }

33ExpandedSubBlockEnd.gif                        }

34InBlock.gif
35InBlock.gif                        s_zones = new TimeZoneInformation[ zones.Count ];
36InBlock.gif
37InBlock.gif                        zones.CopyTo( s_zones );
38ExpandedSubBlockEnd.gif                    }

39ExpandedSubBlockEnd.gif                }

40ExpandedSubBlockEnd.gif            }

41InBlock.gif
42InBlock.gif            return s_zones;
43ExpandedBlockEnd.gif        }


这样我们便获取到了windows所给我们定义好的时区信息,其中TimeZoneInformation.bias代表我做API中所需要的时间偏移量(单位:分钟),至此,我们就可以做出windows所提供的时区之间的任意转换了。


给一个很好的与此相关的代码资料:http://www.codeproject.com/dotnet/WorldClock.asp

参考资料:
http://www.pinvoke.net
http://www.codeproject.com/dotnet/WorldClock.asp

文章转自:http://gamix.cnblogs.com/archive/2005/12/23/303559.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值