[C#.NET] Hexadecimal 字串格式轉時間格式

  • 6817
  • 0
  • C#
  • 2016-07-11

[C#.NET] Hexadecimal 字串格式轉時間格式

這是由某一個設備得知的訊息,我將資料格式整理變成下面的圖,從下圖得知 4DB0026D 會等於 4/21/2011 10:9:49 AM,但要怎麼做?

image

 

我很直覺的認為這是16進制的字串,所以我打算將4DB0026D 轉成Ticks,再轉成DateTime,分別試了Convert / BitConverter 類別進行轉換,結果都不如預期,差了2010年…

image

 

image

 

public byte[] StringToByteArray(string hex)
{
    return Enumerable.Range(0, hex.Length)
                     .Where(x => x % 2 == 0)
                     .Select(x => Convert.ToByte(hex.Substring(x, 2), 16))
                     .ToArray();
}

 

接下來我試著將完整的ticks 轉成 hex,發現原來我的資料格式比正常的資料格式短很多
原始資料格式:4DB0026D
正確資料格式:8CFFD7480FF3A61

image

有了上面的証明,我認為應該是有一個基本的年份日期,而 4DB0026D 是一個偏移數字,可能是 Second 或是 Millisecond,只要將基本的年份日期再加上偏移數字就可以了

開始調整參數,快轉中…

最後用了2000年為基準,再加上 Second ,這時可以發現時間對了,但年份不對,差了30年

image

 

最後將年份調成 1970 就得到正確的結果了。

image

[TestMethod()]
public void ConvertTimeTest()
{
    var expected = "2011/04/21 10:09:49";

    var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);
    var second = Convert.ToInt64("4DB0026D", 16);
    var time = epoch.AddSeconds(secound);

    var actual = time.ToString("yyyy/MM/dd hh:mm:ss");

    Assert.AreEqual(expected, actual);
}

 

結論:

4DB0026D 代表 Second 的意思

若有謬誤,煩請告知,新手發帖請多包涵


Microsoft MVP Award 2010~2017 C# 第四季
Microsoft MVP Award 2018~2022 .NET

Image result for microsoft+mvp+logo