Como: Criar zonas de tempo com regras de ajuste
As informações precisas de fuso horário requeridas por um aplicativo podem não estar presentes em um determinado sistema por diversas razões:
O fuso horário nunca foi definido no registro do sistema local.
Dados sobre o fuso horário foram modificados ou removidos do registro.
O fuso horário não tem informações precisas sobre ajustes de fuso horário para um período específico do histórico.
Nesses casos, você pode chamar o método CreateCustomTimeZone para definir o fuso horário exigido pelo seu aplicativo. Você pode usar as sobrecargas desse método para criar um fuso horário com ou sem regras de ajuste. Se o fuso horário aceitar horário de verão, você pode definir ajustes com regras de ajuste fixas ou flutuantes. (Para obter as definições desses termos, consulte a seção " Terminologia de fuso horário" em Visão geral do fuso horário.)
Importante |
---|
Fusos horários personalizados criados ao chamar o método CreateCustomTimeZone não são adicionados ao registro.Em vez disso, eles podem ser acessados apenas pela referência de objeto retornada pela chamada de método CreateCustomTimeZone. |
Este tópico mostra como criar um fuso horário com regras de ajuste. Para criar um fuso horário que não permite regras de ajuste de horário de verão, consulte Como: Criar zonas de tempo sem regras de ajuste.
Para criar um fuso horário com regras de ajuste flutuantes
Para cada ajuste (isto é, para cada transição para e a partir do horário padrão em um intervalo de tempo específico), faça o seguinte:
Defina a hora de início de transição para o ajuste de fuso horário.
Você deve chamar o método TimeZoneInfo.TransitionTime.CreateFloatingDateRule e passar a ele um valor DateTime que define a hora de transição, um valor inteiro que define o mês de transição, um valor inteiro que define a semana em que ocorre a transição, e um valor DayOfWeek que define o dia da semana em que ocorre a transição. Esta chamada de método instancia um objeto TimeZoneInfo.TransitionTime.
Defina a hora de início de transição para o ajuste de fuso horário. Isso requer uma outra chamada para o método TimeZoneInfo.TransitionTime.CreateFloatingDateRule. Esta chamada de método instancia um segundo objeto TimeZoneInfo.TransitionTime.
Chame o método CreateAdjustmentRule e passe a ele as datas efetivas do início e final do ajuste, um objeto TimeSpan que define o período de tempo na transição, e os dois objetos TimeZoneInfo.TransitionTime que definem quando ocorrem as transições de e para o horário de verão. Esta chamada de método instancia um objeto TimeZoneInfo.AdjustmentRule.
Atribua o objeto TimeZoneInfo.AdjustmentRule a uma matriz de objetos TimeZoneInfo.AdjustmentRule.
Defina o nome de exibição do fuso horário. O nome de exibição segue um formato razoavelmente padrão no qual o deslocamento do Tempo Universal Coordenado (UTC) do fuso horário é colocado entre parênteses e é seguido por uma sequência de caracteres que identifica o fuso horário, uma ou mais das cidades no fuso horário, ou um ou mais dos países ou regiões no fuso horário.
Defina o nome do horário padrão do fuso horário. Normalmente, essa sequência de caracteres também é usada como identificador do fuso horário.
Defina o nome do horário de verão do fuso horário.
Se você desejar usar um identificador diferente do nome padrão do fuso horário, defina o identificador do fuso horário.
Crie uma instância de um objeto TimeSpan que define o deslocamento do UTC do fuso horário. Fusos horários com horários posteriores ao UTC têm um deslocamento positivo. Fusos horários com horários anteriores ao UTC têm um deslocamento negativo.
Chame o método TimeZoneInfo.CreateCustomTimeZone(String, TimeSpan, String, String, String, TimeZoneInfo.AdjustmentRule[]) para instanciar o novo fuso horário.
Exemplo
O exemplo a seguir define uma Fuso Horário Padrão Central para o Estados Unidos que inclui as regras de ajuste para uma variedade de intervalos de tempo desde 1918 até o presente.
Dim cst As TimeZoneInfo
' Declare necessary TimeZoneInfo.AdjustmentRule objects for time zone
Dim delta As New TimeSpan(1, 0, 0)
Dim adjustment As TimeZoneInfo.AdjustmentRule
Dim adjustmentList As New List(Of TimeZoneInfo.AdjustmentRule)
' Declare transition time variables to hold transition time information
Dim transitionRuleStart, transitionRuleEnd As TimeZoneInfo.TransitionTime
' Define new Central Standard Time zone 6 hours earlier than UTC
' Define rule 1 (for 1918-1919)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#02:00:00AM#, 03, 05, DayOfWeek.Sunday)
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#02:00:00AM#, 10, 05, DayOfWeek.Sunday)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1918#, #12/31/1919#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define rule 2 (for 1942)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(#2:00:00AM#, 02, 09)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1942#, #12/31/1942#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define rule 3 (for 1945)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(#11:00:00PM#, 08, 14)
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFixedDateRule(#2:00:00AM#, 09, 30)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1945#, #12/31/1945#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define end rule (for 1967-2006)
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#02:00:00AM#, 10, 5, DayOfWeek.Sunday)
' Define rule 4 (for 1967-73)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#2:00:00AM#, 04, 05, DayOfWeek.Sunday)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1967#, #12/31/1973#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define rule 5 (for 1974 only)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(#2:00:00AM#, 01, 06)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1974#, #12/31/1974#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define rule 6 (for 1975 only)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(#2:00:00AM#, 02, 23)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1975#, #12/31/1975#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define rule 7 (1976-1986)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#2:00:00AM#, 04, 05, DayOfWeek.Sunday)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1976#, #12/31/1986#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define rule 8 (1987-2006)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#2:00:00AM#, 04, 01, DayOfWeek.Sunday)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/1987#, #12/31/2006#, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Define rule 9 (2007- )
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#2:00:00AM#, 03, 02, DayOfWeek.Sunday)
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(#2:00:00AM#, 11, 01, DayOfWeek.Sunday)
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(#01/01/2007#, Date.MaxValue.Date, delta, transitionRuleStart, transitionRuleEnd)
adjustmentList.Add(adjustment)
' Convert list of adjustment rules to an array
Dim adjustments(adjustmentList.Count - 1) As TimeZoneInfo.AdjustmentRule
adjustmentList.CopyTo(adjustments)
cst = TimeZoneInfo.CreateCustomTimeZone("Central Standard Time", New TimeSpan(-6, 0, 0), _
"(GMT-06:00) Central Time (US Only)", "Central Standard Time", _
"Central Daylight Time", adjustments)
TimeZoneInfo cst;
// Declare necessary TimeZoneInfo.AdjustmentRule objects for time zone
TimeSpan delta = new TimeSpan(1, 0, 0);
TimeZoneInfo.AdjustmentRule adjustment;
List<TimeZoneInfo.AdjustmentRule> adjustmentList = new List<TimeZoneInfo.AdjustmentRule>();
// Declare transition time variables to hold transition time information
TimeZoneInfo.TransitionTime transitionRuleStart, transitionRuleEnd;
// Define new Central Standard Time zone 6 hours earlier than UTC
// Define rule 1 (for 1918-1919)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 03, 05, DayOfWeek.Sunday);
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 10, 05, DayOfWeek.Sunday);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1918, 1, 1), new DateTime(1919, 12, 31), delta,
transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define rule 2 (for 1942)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(new DateTime(1, 1, 1, 2, 0, 0), 02, 09);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1942, 1, 1), new DateTime(1942, 12, 31),
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define rule 3 (for 1945)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(new DateTime(1, 1, 1, 23, 0, 0), 08, 14);
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFixedDateRule(new DateTime(1, 1, 1, 2, 0, 0), 09, 30);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1945, 1, 1), new DateTime(1945, 12, 31),
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define end rule (for 1967-2006)
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 10, 5, DayOfWeek.Sunday);
// Define rule 4 (for 1967-73)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 04, 05, DayOfWeek.Sunday);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1967, 1, 1), new DateTime(1973, 12, 31),
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define rule 5 (for 1974 only)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(new DateTime(1, 1, 1, 2, 0, 0), 01, 06);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1974, 1, 1), new DateTime(1974, 12, 31),
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define rule 6 (for 1975 only)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFixedDateRule(new DateTime(1, 1, 1, 2, 0, 0), 02, 23);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1975, 1, 1), new DateTime(1975, 12, 31),
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define rule 7 (1976-1986)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 04, 05, DayOfWeek.Sunday);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1976, 1, 1), new DateTime(1986, 12, 31),
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define rule 8 (1987-2006)
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 04, 01, DayOfWeek.Sunday);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(1987, 1, 1), new DateTime(2006, 12, 31),
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Define rule 9 (2007- )
transitionRuleStart = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 03, 02, DayOfWeek.Sunday);
transitionRuleEnd = TimeZoneInfo.TransitionTime.CreateFloatingDateRule(new DateTime(1, 1, 1, 2, 0, 0), 11, 01, DayOfWeek.Sunday);
adjustment = TimeZoneInfo.AdjustmentRule.CreateAdjustmentRule(new DateTime(2007, 1, 1), DateTime.MaxValue.Date,
delta, transitionRuleStart, transitionRuleEnd);
adjustmentList.Add(adjustment);
// Convert list of adjustment rules to an array
TimeZoneInfo.AdjustmentRule[] adjustments = new TimeZoneInfo.AdjustmentRule[adjustmentList.Count];
adjustmentList.CopyTo(adjustments);
cst = TimeZoneInfo.CreateCustomTimeZone("Central Standard Time", new TimeSpan(-6, 0, 0),
"(GMT-06:00) Central Time (US Only)", "Central Standard Time",
"Central Daylight Time", adjustments);
O fuso horário criado nesse exemplo tem várias regras de ajuste. Deve-se ter cuidado para garantir que as datas eficazes de início e fim de qualquer regra de ajuste não se sobreponham às datas de outra regra de ajuste. Se houver uma sobreposição, um InvalidTimeZoneException será apresentado.
Para regras de ajuste flutuantes, o valor 5 é passado para o parâmetro week do método CreateFloatingDateRule para indicar que a transição ocorre na última semana de um mês específico
Na criação da matriz de objetos TimeZoneInfo.AdjustmentRule para usar na chama de método TimeZoneInfo.CreateCustomTimeZone(String, TimeSpan, String, String, String, TimeZoneInfo.AdjustmentRule[]), o código pôde inicializar a matriz para o tamanho exigido pelo número de ajustes a serem criados pelo fuso horário. Em vez disso, este exemplo de código chama o método Add para adicionar cada regra de ajuste a uma coleção genérica List<T> de objetos TimeZoneInfo.AdjustmentRule. O código chama, então, o método CopyTo para copiar os membros dessa coleção para a matriz.
O exemplo também usa o método CreateFixedDateRule para definir ajustes com data fixa. Isso é semelhante a chamar o método CreateFloatingDateRule, exceto pelo fato de que ele requer somente a hora, mês e dia dos parâmetros de transição.
O exemplo pode ser testado usando um código como o seguinte:
Dim est As TimeZoneInfo = TimeZoneInfo.FindSystemTimeZoneById("Eastern Standard Time")
Dim pastDate1 As Date = #2/11/1942#
Console.WriteLine("Is {0} daylight saving time: {1}", pastDate1, _
cst.IsDaylightSavingTime(pastDate1))
Dim pastDate2 As Date = #10/29/1967 1:30AM#
Console.WriteLine("Is {0} ambiguous: {1}", pastDate2, _
cst.IsAmbiguousTime(pastDate2))
Dim pastDate3 As Date = #1/7/1974 2:59AM#
Console.WriteLine("{0} {1} is {2} {3}", pastDate3, _
IIf(est.IsDaylightSavingTime(pastDate3), _
est.DaylightName, est.StandardName), _
TimeZoneInfo.ConvertTime(pastDate3, est, cst), _
IIf(cst.IsDaylightSavingTime(TimeZoneInfo.ConvertTime(pastDate3, est, cst)), _
cst.DaylightName, cst.StandardName))
'
' This code produces the following output to the console:
'
' Is 2/11/1942 12:00:00 AM daylight saving time: True
' Is 10/29/1967 1:30:00 AM ambiguous: True
' 1/7/1974 2:59:00 AM Eastern Standard Time is 1/7/1974 2:59:00 AM Central Daylight Time
TimeZoneInfo est = TimeZoneInfo.FindSystemTimeZoneById("Eastern Standard Time");
DateTime pastDate1 = new DateTime(1942, 2, 11);
Console.WriteLine("Is {0} daylight saving time: {1}", pastDate1,
cst.IsDaylightSavingTime(pastDate1));
DateTime pastDate2 = new DateTime(1967, 10, 29, 1, 30, 00);
Console.WriteLine("Is {0} ambiguous: {1}", pastDate2,
cst.IsAmbiguousTime(pastDate2));
DateTime pastDate3 = new DateTime(1974, 1, 7, 2, 59, 00);
Console.WriteLine("{0} {1} is {2} {3}", pastDate3,
est.IsDaylightSavingTime(pastDate3) ?
est.DaylightName : est.StandardName,
TimeZoneInfo.ConvertTime(pastDate3, est, cst),
cst.IsDaylightSavingTime(TimeZoneInfo.ConvertTime(pastDate3, est, cst)) ?
cst.DaylightName : cst.StandardName);
//
// This code produces the following output to the console:
//
// Is 2/11/1942 12:00:00 AM daylight saving time: True
// Is 10/29/1967 1:30:00 AM ambiguous: True
// 1/7/1974 2:59:00 AM Eastern Standard Time is 1/7/1974 2:59:00 AM Central Daylight Time
Compilando o código
Este exemplo requer:
Que uma referência a System.Core.dll seja adicionada ao projeto.
Que os seguintes espaços de nome sejam importados:
Imports System.Collections.Generic Imports System.Collections.ObjectModel
using System.Collections.Generic; using System.Collections.ObjectModel;
Consulte também
Tarefas
Como: Criar zonas de tempo sem regras de ajuste