【问题标题】:Sync two DateTimes同步两个日期时间
【发布时间】:2018-07-12 06:25:37
【问题描述】:

我想将远程设备的时钟与另一台设备同步,而不是不断请求远程设备的时间。

我想知道我的设备和远程设备上的时间之间的差异,所以我可以将远程设备的时间戳添加到事件中。

我目前的解决方案是:获取远程设备的时间,并通过比较来计算差异。

例如:

DateTime myDevice = DateTime.Now();          
DateTime remoteDevice = getDateTimeOfRemoteDevice();

//Compare the clocks and keep the difference...    
int daydiff = myDevice.Day - remoteDevice.Day          
int monthdiff = myDevice.Month - RemoteDevice.Month

// ...and so on un till i have everything separated.

我的问题是:有没有更好的方法来做到这一点?

可能类似于:DateTime difference = DateTimeRemoteDevice - DateTimeMyDevice;,答案是:00/00/00 00:01:50,这将允许我随时重新计算远程设备上的时间(包括天月和年的差异)。

【问题讨论】:

  • DateTime - DateTime = TimeSpanTimeSpan + DateTime = DateTime。如果你可以简单地尝试一下,为什么要写这么多文字???
  • 为什么要比较每个字段?如果你从另一个 DateTime 中减去一个 DateTime,你会得到一个 TimeSpan,这正是你想要的。
  • 比较像 DateTime 差异 = DateTimeRemoteDevice - DateTimeMyDevice;更适合我的需要。不过谢谢你的回答。
  • 我认为其他设备没有 NTP 支持?如果您想要准确的时间同步,那么您需要做很多工作来支持网络抖动和延迟等内容。 NTP 旨在处理您可能无法找到的所有边缘情况。
  • 远程设备不在我的控制之下,所以不知道上面是否有 ntp。也可能是让它们同步的解决方案(感谢提示)

标签: c# datetime synchronization clock


【解决方案1】:

当您提出建议时,您已经在问题中发布了更简单的答案:DateTime difference = DateTimeRemoteDevice - DateTimeMyDevice;,但您指定返回值是 DateTime 而不是 TimeSpan。这应该可以解决问题:

TimeSpan difference = getDateTimeOfRemoteDevice() - DateTime.Now;

保存此difference 后,您现在可以随时模拟远程设备时间:

DateTime remoteTimestamp = DateTime.Now + difference;

如果你真的想知道difference 代表多少天、小时、分钟等,TimeSpan 类有一些很好的属性可以帮助解决这个问题:

Console.WriteLine($"Local time .... {DateTime.Now}");
Console.WriteLine($"Remote time ... {remoteTimestamp}");
Console.WriteLine(new string('-', Console.WindowWidth));
Console.Write("Remote time is different by: ");
Console.Write($"{difference.Days} days, ");
Console.Write($"{difference.Hours} hours, ");
Console.WriteLine($"{difference.Minutes} minutes;");
Console.WriteLine($"or a total of {difference.TotalMinutes} minutes.");

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

输出

当然,如果远程时间小于当前时间,这些数字就会变为负数:

【讨论】:

  • 哇,正是我想要的。做得好。投票给这个作为一个完美的答案。感谢您抽出时间制作示例并为您提供解决方案!亲切的问候,文斯
【解决方案2】:

为什么不使用差异作为 TimeSpan?

class TimeSpan{
    public double TotalMilliseconds { get; }
    public double TotalHours { get; }
    public double TotalDays { get; }
    public int Seconds { get; }
    public int Minutes { get; }
    public int Milliseconds { get; }
    public int Hours { get; }
    public int Days { get; }
    public long Ticks { get; }
    public double TotalMinutes { get; }
    public double TotalSeconds { get; }
    ...
}

只需减去两个日期:

TimeSpan outresult = d2.Subtract(d1);

或者只是

TimeSpan outresult = d2 - d1;

【讨论】:

  • 日期时间已经是subtraction operator overloaded。与其发布一个令人困惑的 TimeSpan 类的小表示(对我来说,它建议应该创建一个名为 TimeSpan 的新类),不如链接actual documentation...
  • 感谢您的快速回复。我猜你想参考 Compare(DateTime, DateTime) 比较两个 DateTime 实例并返回一个整数,表示第一个实例是早于、相同还是晚于第二个实例。如您所见,您得到了一个整数。我想返回一种日期时间戳,这样我就可以将它与我的设备 DateTime.now 一起添加,如果它是 neg 或 pos,它将自动成为正确的时间
  • @vincentstrobbe 比较与什么有什么关系?你想要两个日期之间的时间差对吗?如果您实际阅读此答案中的代码,您会看到返回的是 TimeSpan,而不是 int。
  • 我可以计算日、月、年和时间小时、分钟和秒,并使用比较来注意它是负数还是正数。但也许有更好/更好的方法来做到这一点。所以,如果你知道,请告诉我。但无论如何你已经帮助了我:) 谢谢!
  • @vincentstrobbe 3 个人现在已经告诉您如何解决您的问题。你还在纠结什么? TimeSpan 可以是负数也可以是正数,此外它还为您提供了两个 DateTime 之间的确切时间跨度。我们缺少什么?
【解决方案3】:

即使在接受答案后,您的 cmets 仍向我表明您不了解 TimeSpan 的真正含义。

在您的情况下,您有两个日期:

DateTime myDevice = new DateTime(2017, 12, 31); //This would be DateTime.Now
DateTime remoteDevice = new DateTime(2018, 1, 12); //This comes from a method

如果您想知道这两个 DateTime 之间的时间差,只需将一个相减即可:

TimeSpan negativeTimeSpan = myDevice - remoteDevice;
//negativeTimeSpan is: "-12.00:00:00"

TimeSpan positiveTimeSpan = laterDate - earlyDate;
//positiveTimeSpan  is: "12.00:00:00"

您现在不需要任何其他代码。 TimeSpan 甚至具有名为TotalDaysTotalHours 等的属性,可以显示时间差异,以不同的单位衡量。

我给你做了一个小提琴here,你可以在其中看到它的全部作用。

【讨论】:

    【解决方案4】:

    这里是一个基于age calculation的简单例子

                DateTime myDevice = DateTime.Now;
                DateTime remoteDevice = new DateTime(2000, 05, 05, 0, 0, 0); //for example
                TimeSpan difference = myDevice - remoteDevice;  // use timespan for substraction
    

    对于输出,您可以使用timespan 属性

     Console.WriteLine("Remote time is diffrent by "+difference.Days +" days "+difference.Hours+", hours and"+difference.Minutes+" minutes");
    

    但如果您希望在数年或数月内退出,则需要转换为 datetime

    // converting
                DateTime result = DateTime.MinValue + difference;
                // Min value is 01/01/0001
                // subtract our addition or 1 on all components to get the actual date.
                int years = result.Year - 1;
                int months = result.Month - 1;
                //you can continiue
                Console.WriteLine("Remote time is diffrent by " + years + " years and " + months + " months ");
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-01-04
      • 1970-01-01
      • 2017-12-18
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多