【问题标题】:C# NLog Performance Class VariableC# NLog 性能类变量
【发布时间】:2018-04-23 12:59:07
【问题描述】:

使用 NLog 似乎大大降低了我访问类变量的速度。当我按原样运行代码时,s1 比 s2 慢大约 2 倍,这是预期的。但是当我取消注释 GetCurrentClassLogger 行时,s1 变得比 s2 慢 800 倍。我正在使用 .NET Core 2 和 NLog 4.5.3。这是预期的行为吗?是什么导致这种性能下降?感谢您的所有帮助!

class Program
{
    //private static readonly Logger _logger = LogManager.GetCurrentClassLogger();
    private static readonly DateTime _epoch = new DateTime(1970, 1, 1);

    static void Main(string[] args)
    {
        DateTime epoch = new DateTime(1970, 1, 1);
        int count = 10000;
        Stopwatch s1 = new Stopwatch();
        Stopwatch s2 = new Stopwatch();

        s1.Start();
        for (int i = 0; i < count; i++)
        {
            var x = DateTime.UtcNow.Subtract(_epoch).TotalSeconds;
        }

        s1.Stop();

        s2.Start();
        for (int i = 0; i < count; i++)
        {
            var x = DateTime.UtcNow.Subtract(epoch).TotalSeconds;
        }

        s2.Stop();

        Console.WriteLine(s1.ElapsedTicks);
        Console.WriteLine(s2.ElapsedTicks);
        Console.ReadLine();
    }
}

【问题讨论】:

  • 我无法重现这一点 - 我对 s1s2 两次都得到大致相同的结果。我正在使用/o+ /debug- 从命令行编译和运行它 - 你如何测试它?

标签: c# performance nlog


【解决方案1】:

当您第一次访问类中的一个字段时,系统需要初始化该类中的所有静态字段 - 您的基准正在测量这次。注释掉第一行,这只是将_epoch 设置为一个新的DateTime 实例。加入第一行后,这也调用了 NLog 代码来初始化记录器。

您第一次访问类中的字段是在您的第一个循环中,当您访问_epoch 时。这意味着它在s1 之内,所以这也测量了类初始化时间。如果您像这样修改代码:

class Program
{
    private static readonly Logger _logger = LogManager.GetCurrentClassLogger();
    private static readonly DateTime _epoch = new DateTime(1970, 1, 1);

    static void Main(string[] args)
    {

        DateTime epoch = new DateTime(1970, 1, 1);
        int count = 10000;
        Stopwatch s1 = new Stopwatch();
        Stopwatch s2 = new Stopwatch();

        Stopwatch s3 = new Stopwatch();
        s3.Start();
        var e = _epoch;
        s3.Stop();

        s1.Start();
        for (int i = 0; i < count; i++)
        {
            var x = DateTime.UtcNow.Subtract(_epoch).TotalSeconds;
        }

        s1.Stop();

        s2.Start();
        for (int i = 0; i < count; i++)
        {
            var x = DateTime.UtcNow.Subtract(epoch).TotalSeconds;
        }

        s2.Stop();
        Console.WriteLine(s3.ElapsedTicks);
        Console.WriteLine(s1.ElapsedTicks);
        Console.WriteLine(s2.ElapsedTicks);
        Console.ReadLine();
    }
}

您可以看到大部分时间都花在了 s3 中,因为_epoch 的访问权限在那里,它正在初始化那些静态成员。

【讨论】:

    猜你喜欢
    • 2011-07-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-07-02
    • 1970-01-01
    • 2016-09-15
    • 1970-01-01
    相关资源
    最近更新 更多