날짜 및 시간을 사용하는 모든 애플리케이션에서 표준 시간대 간의 차이를 처리하는 것이 점점 더 중요해지고 있습니다. 애플리케이션은 더 이상 모든 시간을 DateTime 구조에서 제공되는 현지 시간으로 표현할 수 있다고 가정할 수 없습니다. 예를 들어 미국 동부 지역의 현재 시간을 표시하는 웹 페이지는 동아시아의 고객에 대한 신뢰성이 부족합니다. 이 문서에서는 시간대 간 시간 변환과 시간대 인식이 제한된 DateTimeOffset 값을 변환하는 방법을 설명합니다.
협정 세계시로 변환
UTC(협정 세계시)는 정밀도가 높은 원자성 시간 표준입니다. 전 세계의 표준 시간대는 UTC의 양수 또는 음수 오프셋으로 표현됩니다. 따라서 UTC는 시간대에 구애받지 않거나 시간대에 중립적인 시간을 제공합니다. 컴퓨터에서 날짜 및 시간의 이식성이 중요한 경우 UTC를 사용하는 것이 좋습니다. 날짜 및 시간을 사용하는 세부 정보 및 기타 모범 사례는 .NET Framework에서 DateTime을 사용하는 코딩 모범 사례를 참조하세요. 개별 표준 시간대를 UTC로 변환하면 시간을 쉽게 비교할 수 있습니다.
비고
단일 시점을 DateTimeOffset 명확하게 나타내도록 구조체를 직렬화할 수도 있습니다. DateTimeOffset 개체는 UTC의 오프셋과 함께 날짜 및 시간 값을 저장하므로 항상 UTC와 관련하여 특정 시점을 나타냅니다.
시간을 UTC로 변환하는 가장 쉬운 방법은 (static
Visual Basic에서) Shared
메서드를 TimeZoneInfo.ConvertTimeToUtc(DateTime) 호출하는 것입니다. 메서드에서 수행하는 정확한 변환은 다음 표와 같이 매개 변수 속성의 dateTime
값 Kind 에 따라 달라집니다.
DateTime.Kind |
변환 |
---|---|
DateTimeKind.Local |
현지 시간을 UTC로 변환합니다. |
DateTimeKind.Unspecified |
매개 변수가 dateTime 현지 시간이라고 가정하고 현지 시간을 UTC로 변환합니다. |
DateTimeKind.Utc |
변경되지 않은 매개 변수를 dateTime 반환합니다. |
다음 코드는 현재 현지 시간을 UTC로 변환하고 결과를 콘솔에 표시합니다.
DateTime dateNow = DateTime.Now;
Console.WriteLine($"The date and time are {TimeZoneInfo.ConvertTimeToUtc(dateNow)} UTC.");
Dim dateNow As Date = Date.Now
Console.WriteLine("The date and time are {0} UTC.", _
TimeZoneInfo.ConvertTimeToUtc(dateNow))
날짜 및 시간 값이 현지 시간 또는 UTC를 나타내지 않으면 메서드가 ToUniversalTime 잘못된 결과를 반환할 가능성이 높습니다. 그러나 이 메서드를 TimeZoneInfo.ConvertTimeToUtc 사용하여 지정된 표준 시간대에서 날짜와 시간을 변환할 수 있습니다. 대상 표준 시간대를 나타내는 개체를 검색하는 TimeZoneInfo 방법은 로컬 시스템에 정의된 표준 시간대 찾기를 참조하세요. 다음 코드에서는 이 메서드를 TimeZoneInfo.ConvertTimeToUtc 사용하여 동부 표준시를 UTC로 변환합니다.
DateTime easternTime = new DateTime(2007, 01, 02, 12, 16, 00);
string easternZoneId = "Eastern Standard Time";
try
{
TimeZoneInfo easternZone = TimeZoneInfo.FindSystemTimeZoneById(easternZoneId);
Console.WriteLine($"The date and time are {TimeZoneInfo.ConvertTimeToUtc(easternTime, easternZone)} UTC.");
}
catch (TimeZoneNotFoundException)
{
Console.WriteLine($"Unable to find the {easternZoneId} zone in the registry.");
}
catch (InvalidTimeZoneException)
{
Console.WriteLine($"Registry data on the {easternZoneId} zone has been corrupted.");
}
Dim easternTime As New Date(2007, 01, 02, 12, 16, 00)
Dim easternZoneId As String = "Eastern Standard Time"
Try
Dim easternZone As TimeZoneInfo = TimeZoneInfo.FindSystemTimeZoneById(easternZoneId)
Console.WriteLine("The date and time are {0} UTC.", _
TimeZoneInfo.ConvertTimeToUtc(easternTime, easternZone))
Catch e As TimeZoneNotFoundException
Console.WriteLine("Unable to find the {0} zone in the registry.", _
easternZoneId)
Catch e As InvalidTimeZoneException
Console.WriteLine("Registry data on the {0} zone has been corrupted.", _
easternZoneId)
End Try
TimeZoneInfo.ConvertTimeToUtc 메서드는 TimeZoneInfo.ConvertTimeToUtc 개체의 DateTime 속성과 표준 시간대가 일치하지 않으면 Kind을(를) 던집니다. Kind 속성이 DateTimeKind.Local이지만 TimeZoneInfo 개체가 현지 표준 시간대를 나타내지 않거나, Kind 속성이 DateTimeKind.Utc인데 TimeZoneInfo 개체가 TimeZoneInfo.Utc가 아닌 경우 불일치가 발생합니다.
모든 이러한 메서드는 DateTime 값을 매개변수로 받아 DateTime 값을 반환합니다. 값의 경우, DateTimeOffset 구조체에는 현재 인스턴스의 날짜와 시간을 UTC로 변환하는 DateTimeOffset 인스턴스 메서드가 있습니다. 다음 예제에서는 메서드를 ToUniversalTime 호출하여 현지 시간을 여러 번 UTC로 변환합니다.
DateTimeOffset localTime, otherTime, universalTime;
// Define local time in local time zone
localTime = new DateTimeOffset(new DateTime(2007, 6, 15, 12, 0, 0));
Console.WriteLine($"Local time: {localTime}");
Console.WriteLine();
// Convert local time to offset 0 and assign to otherTime
otherTime = localTime.ToOffset(TimeSpan.Zero);
Console.WriteLine($"Other time: {otherTime}");
Console.WriteLine($"{localTime} = {otherTime}: {localTime.Equals(otherTime)}");
Console.WriteLine($"{localTime} exactly equals {otherTime}: {localTime.EqualsExact(otherTime)}");
Console.WriteLine();
// Convert other time to UTC
universalTime = localTime.ToUniversalTime();
Console.WriteLine($"Universal time: {universalTime}");
Console.WriteLine($"{otherTime} = {universalTime}: {universalTime.Equals(otherTime)}");
Console.WriteLine($"{otherTime} exactly equals {universalTime}: {universalTime.EqualsExact(otherTime)}");
Console.WriteLine();
// The example produces the following output to the console:
// Local time: 6/15/2007 12:00:00 PM -07:00
//
// Other time: 6/15/2007 7:00:00 PM +00:00
// 6/15/2007 12:00:00 PM -07:00 = 6/15/2007 7:00:00 PM +00:00: True
// 6/15/2007 12:00:00 PM -07:00 exactly equals 6/15/2007 7:00:00 PM +00:00: False
//
// Universal time: 6/15/2007 7:00:00 PM +00:00
// 6/15/2007 7:00:00 PM +00:00 = 6/15/2007 7:00:00 PM +00:00: True
// 6/15/2007 7:00:00 PM +00:00 exactly equals 6/15/2007 7:00:00 PM +00:00: True
Dim localTime, otherTime, universalTime As DateTimeOffset
' Define local time in local time zone
localTime = New DateTimeOffset(#6/15/2007 12:00:00PM#)
Console.WriteLine("Local time: {0}", localTime)
Console.WriteLine()
' Convert local time to offset 0 and assign to otherTime
otherTime = localTime.ToOffset(TimeSpan.Zero)
Console.WriteLine("Other time: {0}", otherTime)
Console.WriteLine("{0} = {1}: {2}", _
localTime, otherTime, _
localTime.Equals(otherTime))
Console.WriteLine("{0} exactly equals {1}: {2}", _
localTime, otherTime, _
localTime.EqualsExact(otherTime))
Console.WriteLine()
' Convert other time to UTC
universalTime = localTime.ToUniversalTime()
Console.WriteLine("Universal time: {0}", universalTime)
Console.WriteLine("{0} = {1}: {2}", _
otherTime, universalTime, _
universalTime.Equals(otherTime))
Console.WriteLine("{0} exactly equals {1}: {2}", _
otherTime, universalTime, _
universalTime.EqualsExact(otherTime))
Console.WriteLine()
' The example produces the following output to the console:
' Local time: 6/15/2007 12:00:00 PM -07:00
'
' Other time: 6/15/2007 7:00:00 PM +00:00
' 6/15/2007 12:00:00 PM -07:00 = 6/15/2007 7:00:00 PM +00:00: True
' 6/15/2007 12:00:00 PM -07:00 exactly equals 6/15/2007 7:00:00 PM +00:00: False
'
' Universal time: 6/15/2007 7:00:00 PM +00:00
' 6/15/2007 7:00:00 PM +00:00 = 6/15/2007 7:00:00 PM +00:00: True
' 6/15/2007 7:00:00 PM +00:00 exactly equals 6/15/2007 7:00:00 PM +00:00: True
UTC를 지정된 표준 시간대로 변환
UTC를 현지 시간으로 변환하려면 다음 UTC를 현지 시간으로 변환 섹션을 참조하세요. UTC를 지정한 표준 시간대의 시간으로 변환하려면 메서드를 호출합니다 ConvertTimeFromUtc . 이 메서드는 다음 두 개의 매개 변수를 사용합니다.
다음 코드는 UTC를 중앙 표준시로 변환합니다.
DateTime timeUtc = DateTime.UtcNow;
try
{
TimeZoneInfo cstZone = TimeZoneInfo.FindSystemTimeZoneById("Central Standard Time");
DateTime cstTime = TimeZoneInfo.ConvertTimeFromUtc(timeUtc, cstZone);
Console.WriteLine("The date and time are {0} {1}.",
cstTime,
cstZone.IsDaylightSavingTime(cstTime) ?
cstZone.DaylightName : cstZone.StandardName);
}
catch (TimeZoneNotFoundException)
{
Console.WriteLine("The registry does not define the Central Standard Time zone.");
}
catch (InvalidTimeZoneException)
{
Console.WriteLine("Registry data on the Central Standard Time zone has been corrupted.");
}
Dim timeUtc As Date = Date.UtcNow
Try
Dim cstZone As TimeZoneInfo = TimeZoneInfo.FindSystemTimeZoneById("Central Standard Time")
Dim cstTime As Date = TimeZoneInfo.ConvertTimeFromUtc(timeUtc, cstZone)
Console.WriteLine("The date and time are {0} {1}.", _
cstTime, _
IIf(cstZone.IsDaylightSavingTime(cstTime), _
cstZone.DaylightName, cstZone.StandardName))
Catch e As TimeZoneNotFoundException
Console.WriteLine("The registry does not define the Central Standard Time zone.")
Catch e As InvalidTimeZoneException
Console.WriteLine("Registry data on the Central Standard Time zone has been corrupted.")
End Try
UTC를 현지 시간으로 변환
UTC를 현지 시간으로 변환하려면 변환할 시간을 가진 개체의 ToLocalTime 메서드를 호출 DateTime 합니다. 메서드의 정확한 동작은 다음 표와 같이 개체 Kind 의 속성 값에 따라 달라집니다.
DateTime.Kind |
변환 |
---|---|
DateTimeKind.Local |
DateTime 변경되지 않은 값을 반환합니다. |
DateTimeKind.Unspecified |
값이 DateTime UTC이고 UTC를 현지 시간으로 변환한다고 가정합니다. |
DateTimeKind.Utc |
값을 현지 시간으로 변환합니다 DateTime . |
비고
TimeZone.ToLocalTime 메서드는 DateTime.ToLocalTime
메서드와 동일하게 동작합니다. 변환하려면 날짜 및 시간 값인 단일 매개 변수가 필요합니다.
(static
Visual Basic에서) Shared
메서드를 사용하여 지정된 표준 시간대의 TimeZoneInfo.ConvertTime 시간을 현지 시간으로 변환할 수도 있습니다. 이 기술은 다음 섹션에서 설명합니다.
두 표준 시간대 간 변환
클래스의 다음 두 가지 static
(Shared
는 Visual Basic에서) 메서드를 사용하여 어떤 두 표준 시간대 간에도 변환할 수 있습니다.
-
이 메서드의 매개 변수는 변환할 날짜 및 시간 값,
TimeZoneInfo
날짜 및 시간 값의 표준 시간대를 나타내는 개체 및 날짜 및TimeZoneInfo
시간 값을 변환할 표준 시간대를 나타내는 개체입니다. -
이 메서드의 매개 변수는 변환할 날짜 및 시간 값, 날짜 및 시간 값의 표준 시간대 식별자 및 날짜 및 시간 값을 변환할 표준 시간대의 식별자입니다.
두 메서드 Kind 모두 변환할 날짜 및 시간 값의 속성과 TimeZoneInfo 해당 표준 시간대를 나타내는 개체 또는 표준 시간대 식별자가 서로 일치해야 합니다. 그렇지 않으면 ArgumentException가 던져집니다. 예를 들어 날짜 및 시간 값의 Kind
속성이 DateTimeKind.Local
인 경우, 메서드에 매개 변수로 전달된 TimeZoneInfo
객체가 TimeZoneInfo.Local
와 같지 않으면 예외가 발생합니다. 메서드에 매개 변수로 전달된 식별자가 TimeZoneInfo.Local.Id
와 같지 않으면 예외가 throw됩니다.
다음 예제에서는 이 메서드를 ConvertTime 사용하여 하와이 표준시에서 현지 시간으로 변환합니다.
DateTime hwTime = new DateTime(2007, 02, 01, 08, 00, 00);
try
{
TimeZoneInfo hwZone = TimeZoneInfo.FindSystemTimeZoneById("Hawaiian Standard Time");
Console.WriteLine("{0} {1} is {2} local time.",
hwTime,
hwZone.IsDaylightSavingTime(hwTime) ? hwZone.DaylightName : hwZone.StandardName,
TimeZoneInfo.ConvertTime(hwTime, hwZone, TimeZoneInfo.Local));
}
catch (TimeZoneNotFoundException)
{
Console.WriteLine("The registry does not define the Hawaiian Standard Time zone.");
}
catch (InvalidTimeZoneException)
{
Console.WriteLine("Registry data on the Hawaiian Standard Time zone has been corrupted.");
}
Dim hwTime As Date = #2/01/2007 8:00:00 AM#
Try
Dim hwZone As TimeZoneInfo = TimeZoneInfo.FindSystemTimeZoneById("Hawaiian Standard Time")
Console.WriteLine("{0} {1} is {2} local time.", _
hwTime, _
IIf(hwZone.IsDaylightSavingTime(hwTime), hwZone.DaylightName, hwZone.StandardName), _
TimeZoneInfo.ConvertTime(hwTime, hwZone, TimeZoneInfo.Local))
Catch e As TimeZoneNotFoundException
Console.WriteLine("The registry does not define the Hawaiian Standard Time zone.")
Catch e As InvalidTimeZoneException
Console.WriteLine("Registry data on the Hawaiian Standard Time zone has been corrupted.")
End Try
DateTimeOffset 값 변환
개체가 DateTimeOffset 인스턴스화될 때 해당 표준 시간대에서 연결이 해제되므로 개체가 나타내는 날짜 및 시간 값은 완전히 표준 시간대를 인식하지 못합니다. 그러나 대부분의 경우 애플리케이션은 특정 표준 시간대가 아닌 UTC에서 두 개의 서로 다른 오프셋을 기반으로 날짜와 시간을 변환하기만 하면 됩니다. 이 변환을 수행하려면 현재 인스턴스의 ToOffset 메서드를 호출할 수 있습니다. 메서드의 단일 매개 변수는 메서드가 반환할 새 날짜 및 시간 값의 오프셋입니다.
예를 들어 웹 페이지에 대한 사용자 요청의 날짜 및 시간이 알려져 있고 MM/dd/yyyy hh:mm:ss zzzz 형식의 문자열로 serialize되는 경우 다음 메서드는 ReturnTimeOnServer
이 날짜 및 시간 값을 웹 서버의 날짜 및 시간으로 변환합니다.
public DateTimeOffset ReturnTimeOnServer(string clientString)
{
string format = @"M/d/yyyy H:m:s zzz";
TimeSpan serverOffset = TimeZoneInfo.Local.GetUtcOffset(DateTimeOffset.Now);
try
{
DateTimeOffset clientTime = DateTimeOffset.ParseExact(clientString, format, CultureInfo.InvariantCulture);
DateTimeOffset serverTime = clientTime.ToOffset(serverOffset);
return serverTime;
}
catch (FormatException)
{
return DateTimeOffset.MinValue;
}
}
Public Function ReturnTimeOnServer(clientString As String) As DateTimeOffset
Dim format As String = "M/d/yyyy H:m:s zzz"
Dim serverOffset As TimeSpan = TimeZoneInfo.Local.GetUtcOffset(DateTimeOffset.Now)
Try
Dim clientTime As DateTimeOffset = DateTimeOffset.ParseExact(clientString, format, CultureInfo.InvariantCulture)
Dim serverTime As DateTimeOffset = clientTime.ToOffset(serverOffset)
Return serverTime
Catch e As FormatException
Return DateTimeOffset.MinValue
End Try
End Function
메서드가 UTC보다 5시간 이전 표준 시간대의 날짜 및 시간을 나타내는 "9/1/2007 5:32:07 -05:00" 문자열을 전달하는 경우 미국 태평양 표준 시간대에 있는 서버에 대해 "9/1/2007 오전 3:32:07"을 반환합니다.
또한 TimeZoneInfo 클래스에는 TimeZoneInfo 값을 사용하여 시간대 변환을 수행하는 ToOffset(TimeSpan) 메서드의 오버로드도 포함됩니다. 메서드의 매개 변수는 DateTimeOffset 값과 시간대를 참조하여 시간을 변환하는 데 사용됩니다. 메서드 호출은 값을 반환합니다 DateTimeOffset . 예를 들어 이전 예제의 ReturnTimeOnServer
메서드를 다음과 같이 다시 작성하여 메서드를 호출 ConvertTime(DateTimeOffset, TimeZoneInfo) 할 수 있습니다.
public DateTimeOffset ReturnTimeOnServer(string clientString)
{
string format = @"M/d/yyyy H:m:s zzz";
try
{
DateTimeOffset clientTime = DateTimeOffset.ParseExact(clientString, format,
CultureInfo.InvariantCulture);
DateTimeOffset serverTime = TimeZoneInfo.ConvertTime(clientTime,
TimeZoneInfo.Local);
return serverTime;
}
catch (FormatException)
{
return DateTimeOffset.MinValue;
}
}
Public Function ReturnTimeOnServer(clientString As String) As DateTimeOffset
Dim format As String = "M/d/yyyy H:m:s zzz"
Try
Dim clientTime As DateTimeOffset = DateTimeOffset.ParseExact(clientString, format, CultureInfo.InvariantCulture)
Dim serverTime As DateTimeOffset = TimeZoneInfo.ConvertTime(clientTime, TimeZoneInfo.Local)
Return serverTime
Catch e As FormatException
Return DateTimeOffset.MinValue
End Try
End Function
참고하십시오
.NET