以对数方式记录1,10,100,1000等

Aar*_*ack 5 .net c# logarithm

是否有一种更有效的方法来做到这一点,有些事情只是感觉不对劲?我正在寻找以对数方式记录最有效的方法.

    public bool Read()
    {
        long count = Interlocked.Increment(ref _count);
        switch (count)
        {
            case 1L:
            case 10L:
            case 100L:
            case 1000L:
            case 10000L:
            case 100000L:
            case 1000000L:
            case 10000000L:
            case 100000000L:
            case 1000000000L:
            case 10000000000L:
            case 100000000000L:
            case 1000000000000L:
            case 10000000000000L:
            case 100000000000000L:
            case 10000000000000000L:
            case 100000000000000000L:
            case 1000000000000000000L:
                _logger.LogFormattable(LogLevel.Debug, $"{count} Rows Read");
                break;
        }

        return _reader.Read();
    }
Run Code Online (Sandbox Code Playgroud)

更新:

这是我的微基准测试.

  • 方法1:Übercoder跟上状态的方式
  • 方法2:我使用big switch语句
  • 方法3:Markus Weninger用漂亮的数学函数的方法

因为对我而言,没有记录就读取了100,000,000条记录需要大约20分钟,那么额外的4秒就没有了.我将采用美丽的数学方式做事.Mathod3在我的场景中胜出.

Run time for 100,000,000 iterations averaged over 100 attempts

Method1 Max: 00:00:00.3253789
Method1 Min: 00:00:00.2261253
Method1 Avg: 00:00:00.2417223

Method2 Max: 00:00:00.5295368
Method2 Min: 00:00:00.3618406
Method2 Avg: 00:00:00.3904475

Method3 Max: 00:00:04.0637217
Method3 Min: 00:00:03.2023237
Method3 Avg: 00:00:03.3979303
Run Code Online (Sandbox Code Playgroud)

Mar*_*ger 8

如果性能不是一个大问题,我会使用以下内容

if(Math.Log10(count) % 1 == 0)
  _logger.LogFormattable(LogLevel.Debug, $"{count} Rows Read");
Run Code Online (Sandbox Code Playgroud)

这个问题陈述如下:

对于浮点数,n%1 == 0通常是检查小数点后是否有任何内容的方法.


编辑:要完成我的答案,还可以跟踪下一个日志记录值,如@Übercoder在他的答案中发布的那样.

long nextLoggingValueForLogX = 1;
if (count == nextLoggingValueForLogX )
{
   nextLoggingValueForLogX *= 10; // Increase it by your needs, e.g., logarithmically by multiplying with 10
   _logger.LogFormattable(LogLevel.Debug, $"{count} Rows Read");
}
Run Code Online (Sandbox Code Playgroud)

然而,这种方法将为每次不应执行的日志提供一个新变量.如果必须使线程安全,这将引入额外的代码和额外的工作.