我在服务器和客户端之间转换日期时遇到问题,两者都在德国运行。客户端计算机上的区域设置可以设置为英国或德国。我从服务器接收CET格式的日期,我需要在UI上将此时间表示为英国时间。例如,从服务器收到的时间,例如01/07/2010 01:00:00应该在UI上表示为01/07/2010 00:00:00。我已经为此目的编写了一个转换器,但是在运行它时会产生2小时的时差。下面是代码,请帮忙吗?
public class LocalToGmtConverter : IDateConverter
{
private readonly TimeZoneInfo timeZoneInfo;
public LocalToGmtConverter()
: this(TimeZoneInfo.Local)
{
}
public LocalToGmtConverter(TimeZoneInfo timeZoneInfo)
{
this.timeZoneInfo = timeZoneInfo;
}
public DateTime Convert(DateTime localDate)
{
var utcKind = DateTime.SpecifyKind(localDate, DateTimeKind.Utc);
return utcKind;
}
public DateTime ConvertBack(object fromServer)
{
DateTime serverDate = (DateTime)fromServer;
var utcOffset = timeZoneInfo.GetUtcOffset(serverDate);
var uiTime = serverDate- utcOffset;
return uiTime;
}
}
答案 0 :(得分:18)
我认为您正在转换为UTC(而非英国)时间。由于中欧仍然有夏季时间(如果温度不同,则会发生这种情况),差异是直到10月31日的+2小时。
如果你知道你正在从德国转到英国(即夏天将CEST转为BST,冬季转为CET转到GMT),为什么不减1小时呢?
如果您想要英国的时区信息,可以使用
构建它var britishZone = TimeZoneInfo.FindSystemTimeZoneById("GMT Standard Time");
然后你可以使用
转换日期var newDate = TimeZoneInfo.ConvertTime(serverDate, TimeZoneInfo.Local, britishZone);
答案 1 :(得分:1)
使用TimeZoneInfo.ConvertTime将原始输入时区(CET)转换为目标时区(英国)。
public static DateTime ConvertTime(
DateTime dateTime,
TimeZoneInfo sourceTimeZone,
TimeZoneInfo destinationTimeZone
)
MSDN上的完整指南here:
在时区之间转换时间
来自MSDN的修改代码示例:
DateTime ceTime = new DateTime(2007, 02, 01, 08, 00, 00);
try
{
TimeZoneInfo ceZone = TimeZoneInfo.FindSystemTimeZoneById("Central Europe Standard Time");
TimeZoneInfo gmtZone = TimeZoneInfo.FindSystemTimeZoneById("GMT Standard Time");
Console.WriteLine("{0} {1} is {2} GMT time.",
ceTime,
ceZone.IsDaylightSavingTime(ceTime) ? ceZone.DaylightName : ceZone.StandardName,
TimeZoneInfo.ConvertTime(ceTime, ceZone, gmtZone));
}
catch (TimeZoneNotFoundException)
{
Console.WriteLine("The registry does not define the required timezones.");
}
catch (InvalidTimeZoneException)
{
Console.WriteLine("Registry data on the required timezones has been corrupted.");
}
答案 2 :(得分:0)
处理本地时间的更好方法是将它们存储在统一的表示形式中,例如UTC。
因此,您可以将所有输入时间转换为UTC(通过.ToUniversalTime()
),并存储(或传输)其值。当您需要显示它时,只需使用.ToLocalTime()
转换回来。
因此,您可以避免要求知道哪个时区是原始值,并且可以轻松地在不同的时区显示存储的值。
此外,您还可以避免在下一个时区编写特定逻辑处理时间的问题,并试图找出如何将它们转换为所有可用的。
答案 3 :(得分:0)
这就是我的所作所为:
var request = (HttpWebRequest)HttpWebRequest.Create(link);
request.AutomaticDecompression = DecompressionMethods.GZip;
我需要添加SpecifyKind部分或ConvertTime抛出异常
答案 4 :(得分:-2)
我意识到这个问题适用于C#,但如果您只想进行一次转换,则可以从PowerShell命令行执行此操作:
$d = [DateTime]::Parse("04/02/2014 17:00:00")
$gmt = [TimeZoneInfo]::FindSystemTimeZoneById("GMT Standard Time");
[TimeZoneInfo]::ConvertTime($d, $gmt, [TimeZoneInfo]::Local)
此脚本会将英国时间17:00转换为您当地的时区。 对我来说,这将是CST。有趣的是,如果我将日期设置为2014年3月27日,结果会有所不同,因为英国的夏令时会在不同的日期开始。