1

我需要获取两个给定日期之间的天数。

我使用了“(endDate-startDate).Days”,但我的前辈建议它可能会导致一些内存泄漏,他告诉我如果在 32 位系统和 64 位系统上使用它可能会导致不同的值,并建议我改用 TimeSpan 然后获取天数。

我无法理解这一点。

有人可以解释一下它是如何引起任何内存管理问题的吗?

DateTime dt1 = dateTime.Now;
DateTime dt2 = dateTime.Now.Adddays(-10);
int daysDiff = (dt2-dt1).Days; // I'm doing like this.

TimeSpan ts = dt2-dt1; // this is what my senior-
int daysDiff = ts.Days. // advised me.

如果我错了,请纠正我,因为我在这一点上不是那么精通。在此先感谢,感谢您的帮助。

4

1 回答 1

6

C#代码:

    int YourVersion()
    {
        DateTime dt1 = DateTime.Now;
        DateTime dt2 = DateTime.Now.AddDays(-10);
        int daysDiff = (dt2 - dt1).Days;
        return daysDiff;
    }
    int SeniorVersion()
    {
        DateTime dt1 = DateTime.Now;
        DateTime dt2 = DateTime.Now.AddDays(-10);
        TimeSpan ts = dt2 - dt1;
        int daysDiff = ts.Days;
        return daysDiff;
    }

在VS2013上编译,Release build,反编译IL:

你的:

.method private hidebysig instance int32 
        YourVersion() cil managed
{
  // Code size       48 (0x30)
  .maxstack  2
  .locals init ([0] valuetype [mscorlib]System.DateTime dt1,
           [1] valuetype [mscorlib]System.DateTime dt2,
           [2] int32 daysDiff,
           [3] valuetype [mscorlib]System.DateTime CS$0$0000,
           [4] valuetype [mscorlib]System.TimeSpan CS$0$0001)
  IL_0000:  call       valuetype [mscorlib]System.DateTime [mscorlib]System.DateTime::get_Now()
  IL_0005:  stloc.0
  IL_0006:  call       valuetype [mscorlib]System.DateTime [mscorlib]System.DateTime::get_Now()
  IL_000b:  stloc.3
  IL_000c:  ldloca.s   CS$0$0000
  IL_000e:  ldc.r8     -10.
  IL_0017:  call       instance valuetype [mscorlib]System.DateTime [mscorlib]System.DateTime::AddDays(float64)
  IL_001c:  stloc.1
  IL_001d:  ldloc.1
  IL_001e:  ldloc.0
  IL_001f:  call       valuetype [mscorlib]System.TimeSpan [mscorlib]System.DateTime::op_Subtraction(valuetype [mscorlib]System.DateTime,
                                                                                                     valuetype [mscorlib]System.DateTime)
  IL_0024:  stloc.s    CS$0$0001
  IL_0026:  ldloca.s   CS$0$0001
  IL_0028:  call       instance int32 [mscorlib]System.TimeSpan::get_Days()
  IL_002d:  stloc.2
  IL_002e:  ldloc.2
  IL_002f:  ret
} // end of method Program::YourVersion

你的前辈:

.method private hidebysig instance int32 
        SeniorVersion() cil managed
{
  // Code size       48 (0x30)
  .maxstack  2
  .locals init ([0] valuetype [mscorlib]System.DateTime dt1,
           [1] valuetype [mscorlib]System.DateTime dt2,
           [2] valuetype [mscorlib]System.TimeSpan ts,
           [3] int32 daysDiff,
           [4] valuetype [mscorlib]System.DateTime CS$0$0000)
  IL_0000:  call       valuetype [mscorlib]System.DateTime [mscorlib]System.DateTime::get_Now()
  IL_0005:  stloc.0
  IL_0006:  call       valuetype [mscorlib]System.DateTime [mscorlib]System.DateTime::get_Now()
  IL_000b:  stloc.s    CS$0$0000
  IL_000d:  ldloca.s   CS$0$0000
  IL_000f:  ldc.r8     -10.
  IL_0018:  call       instance valuetype [mscorlib]System.DateTime [mscorlib]System.DateTime::AddDays(float64)
  IL_001d:  stloc.1
  IL_001e:  ldloc.1
  IL_001f:  ldloc.0
  IL_0020:  call       valuetype [mscorlib]System.TimeSpan [mscorlib]System.DateTime::op_Subtraction(valuetype [mscorlib]System.DateTime,
                                                                                                     valuetype [mscorlib]System.DateTime)
  IL_0025:  stloc.2
  IL_0026:  ldloca.s   ts
  IL_0028:  call       instance int32 [mscorlib]System.TimeSpan::get_Days()
  IL_002d:  stloc.3
  IL_002e:  ldloc.3
  IL_002f:  ret
} // end of method Program::SeniorVersion

区别?你的有一个编译器生成的TimeSpan变量,用于保存 的结果dt2 - dt1,而你的高年级有一个命名变量。除此之外,它们是相同的代码。

没有内存泄漏的风险,代码在 32 位和 64 位系统上运行完全相同。

(根据用于访问局部变量的特定指令,存在一些细微差别,但预计不会对 JIT 可以生成的代码产生任何干扰)

于 2013-07-24T06:46:28.007 回答