微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

c# – 为什么在.NET中检查算术有时比未检查更快?

为什么当我打开C#项目属性>下的“检查算术下溢/溢出”时构建>高级,以下代码关闭选项(141毫秒)运行得更快(138毫秒)?

测试运行#1:138ms,带有检查算术,141ms没有

using System;
using System.Diagnostics;

class Program
{
    static void Main(string[] args)
    {
        var s = new Stopwatch();
        s.Start();
        int a = 0;
        for (int i = 0; i < 100000000; i += 3) {
            if (i == 1000)
                i *= 2;
            if (i % 35 == 0)
                ++a;
        }
        s.Stop();
        Console.WriteLine(s.ElapsedMilliseconds);
        Console.WriteLine(a);
    }
}

另一方面,如果您注释掉if(i == 1000)i * = 2;,则检查的代码比未检查的代码(116 ms)运行得慢(120 ms).

测试运行#2:120ms,116ms没有

using System;
using System.Diagnostics;

class Program
{
    static void Main(string[] args)
    {
        var s = new Stopwatch();
        s.Start();
        int a = 0;
        for (int i = 0; i < 100000000; i += 3) {
            if (i % 35 == 0)
                ++a;
        }
        s.Stop();
        Console.WriteLine(s.ElapsedMilliseconds);
        Console.WriteLine(a);
    }
}

进程:重复从PowerShell提示符在Visual Studio外部手动运行.exe,直到结果时间戳保持一致(±1 ms);多次在设置之间翻转以确保一致的结果.

测试盒设置:

> Windows 8.1 Pro x64
> VS2013更新2
>英特尔酷睿i7-4500
>认C#控制台项目模板
>发布配置

解决方法

答案是你正在处理许多常量,这些常量允许JIT做出安全的假设,它永远不会溢出.如果您使用类似Fibbonacci基准的东西,差异就会变得清晰.

2770ms vs 4150ms(Anycpu,32位首选)

using System;
using System.Diagnostics;

class Program
{
    static void Main(string[] args)
    {
        var s = new Stopwatch();
        s.Start();
        int a = 0;
        for (int i = 0; i < 100000000; i++)
        {
            a = Fibonacci(45);
        }
        s.Stop();
        Console.WriteLine(s.ElapsedMilliseconds);
    }

    public static int Fibonacci(int n)
    {
        int a = 0;
        int b = 1;
        for (int i = 0; i < n; i++)
        {
            int temp = a;
            a = b;
            // if the JIT compiler is cLever,only this one needs to be 'checked'
            b = temp + b; 
        }
        return a;
    }

}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐