c# - .NET 装箱/拆箱与类型转换性能

标签 c# .net performance

我试图从性能的角度了解两种解决方案中的哪一种是首选。 比如我有两段代码:

1) 装箱/拆箱

int val = 5;
Session["key"] = val; 
int val2 = (int)Session["key"];

2) 转换(IntObj 有 int Value 属性来存储 int)

IntObj val = new IntObj(5);  
Session["key"] = val;
int val2 = ((IntObj )Session["key"]).Value;

这些例子之间的内存管理区别是什么? 有没有更快的方法来执行此类操作?

注意: Session只是举个例子,可以是任意Dictionary<string, object>

最佳答案

看起来你在这里真正做的是比较手动装箱和内置装箱。内置的装箱已经过高度优化 - 所以我不希望在这里看到巨大的差异,但我们可以检查一下。重要的是,请注意两者具有相同的内存影响:一个堆对象包含一个 int 字段,每个 int 装箱/包装。

以下显示了两个接近的时间几乎相同;因此,我会说,只需以直接/内置的方式将其装箱即可。

注意:在 Release模式下运行它,没有调试器(最好在命令行)。请注意,第一个调用是预先 JIT 一切。

using System;
using System.Diagnostics;
public sealed class IntObj
{
    public readonly int Value;
    public IntObj(int value)
    {
        Value = value;
    }
}
static class Program
{
    static void Main()
    {
        Run(1, 0, false);
        Run(100000, 500, true);
        Console.ReadKey();
    }
    static void Run(int length, int repeat, bool report)
    {
        var data = new object[length];

        int chk = 0;
        var watch = Stopwatch.StartNew();
        for (int j = 0; j < repeat; j++)
        {
            for (int i = 0; i < data.Length; i++)
            {
                data[i] = i;
                chk += i;
            }
        }
        watch.Stop();
        if(report) Console.WriteLine("Box: {0}ms (chk: {1})", watch.ElapsedMilliseconds, chk);
        chk = 0;
        watch = Stopwatch.StartNew();
        for (int j = 0; j < repeat; j++)
        {
            for (int i = 0; i < data.Length; i++)
            {
                chk += (int) data[i];
            }
        }
        watch.Stop();
        if (report) Console.WriteLine("Unbox: {0}ms (chk: {1})", watch.ElapsedMilliseconds, chk);

        chk = 0;
        watch = Stopwatch.StartNew();
        for (int j = 0; j < repeat; j++)
        {
            for (int i = 0; i < data.Length; i++)
            {
                data[i] = new IntObj(i);
                chk += i;
            }
        }
        watch.Stop();
        if (report) Console.WriteLine("Wrap: {0}ms (chk: {1})", watch.ElapsedMilliseconds, chk);
        chk = 0;
        watch = Stopwatch.StartNew();
        for (int j = 0; j < repeat; j++)
        {
            for (int i = 0; i < data.Length; i++)
            {
                chk += ((IntObj)data[i]).Value;
            }
        }
        watch.Stop();
        if (report) Console.WriteLine("Unwrap: {0}ms (chk: {1})", watch.ElapsedMilliseconds, chk);
    }


}

关于c# - .NET 装箱/拆箱与类型转换性能,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12294655/

相关文章:

c# - 为什么 JIT_MethodAccessAllowedBySecurity 花费这么多时间?

c# - 将 2 个表绑定(bind)在一起(一对多关系)

c# - C# 生成的 Excel 工作表中的自动调整列宽

c# - 将 Entity Framework 与 MySQL 数据库一起使用,模型设计器不会选取存储的过程参数

.net - %2b 导致 IIS Hosted Angular 返回 404

c# - Enumerator 结构的可变性

sql-server - SQL Server : Select in vs or?

css - 将 CSS 重置为默认状态

c# - SetWindowPos 不改变最大化状态

javascript - 测量 Javascript 应用程序的 CPU 负载