在C#中将值类型装箱到引用类型时需要多少内存?

在C#中将值类型装箱到引用类型时需要多少内存?,c#,.net,C#,.net,我只想知道obj所需的额外位以及为什么?首先帮助解释C#5规范第4.3.1节装箱转换中的“为什么” 装箱不可为null的值类型的值的实际过程是 最好的解释是想象一个普通拳击课的存在, 其行为就好像它被声明如下: public class A { public static void Main(string[] args) { int num = 13; // It stores in Stack and takes 4 bytes object obj

我只想知道obj所需的额外位以及为什么?

首先帮助解释C#5规范第4.3.1节装箱转换中的“为什么”

装箱不可为null的值类型的值的实际过程是 最好的解释是想象一个普通拳击课的存在, 其行为就好像它被声明如下:

public class A
{
    public static void Main(string[] args)
    {
       int num = 13; // It stores in Stack and takes 4 bytes
       object obj = 13; // Where it is Stored (Stack or Heap)? 
       //How much size obj require?
    }
}
概念上对应于

int i = 123;
object box = i;
下面的语句隐式地将装箱操作应用于 变量一:

int i = 123;
此语句的结果是在 堆栈,它引用堆上int类型的值。这 值是分配给变量i的值类型值的副本。 两个变量i和o之间的差异如所示 下图

因此,在堆栈上存储了
sizeof(Object)
字节,在堆上存储了
sizeof(int)
+类开销

我找不到任何关于开销有多大的好文档,它的大小很可能是8到16个字节。

根据每个对象的标题,32位系统的开销是8个字节,64位系统的开销是16个字节。这意味着,在32位系统上,装箱整数将占用堆上的12个字节和堆栈上的4个字节引用,在64位系统上占用堆上的20个字节和堆栈上的8个字节。然而,根据@Hans Passant的评论,对象必须在32位模式下与4字节的倍数对齐,在64字节模式下与8字节的倍数对齐,这将使64位版本占用24字节


应该注意的是,这是一个实施细节,将来可能会发生变化。总的来说,你会关心这件事是很奇怪的。在处理值类型时,CPU时间通常比内存问题大得多,因为装箱会给GC带来负载,并且需要额外的操作来使用对象。

num
可能存储在堆栈中,也可能不存储在堆栈中。事实上,对于您的程序来说,在没有附加调试器的情况下以发布模式运行时,它很可能根本不会被存储,因为编译器将检测到从未使用过
num
,也不会存储该值。你在做什么,知道你问题的答案会影响你的设计选择?感谢Scott的知识,但让我们假设它在以后的程序中使用,我只需要知道内存差异。内存差异=不重要。你不应该需要大量的盒装值。我相当肯定这个计算是错误的。每个对象的开销都比指针大小高得多。感谢您提供的知识:)@develhpal不要说“谢谢”,如果答案有帮助,请向上投票。如果您觉得您的问题已经得到了回答,请单击您认为最能回答您的问题的问题旁边的复选标记。这几乎是正确的,但是你忘记了填充。只需记录对象大小是32位中4的倍数,64位中8的倍数。在64位模式下,向装箱整数添加4个字节的填充,即24个字节。装箱字节是更有趣的情况,32位模式下3字节的填充,64位模式下7字节的填充。感谢您的知识:)
int i = 123;
object box = new Box<int>(i);
int i = 123;
// Boxing copies the value of i into object o. 
object o = i;