C#引用类型在传递给方法时是否分配新内存?

时间:2010-11-04 23:04:59

标签: c# reference memory-management

每个人......我是C#和其他语言的新手......

我读过Skeet的两篇文章,一篇关于heap/stack,另一篇关于reference types and value types。我认为我的问题很简单,但在阅读这些文章之后,我并没有向他澄清。

引用类型是否在传递给方法时分配新内存?

例如,如果我将表单传递给方法,例如

void myMethod(System.Windows.Forms.Form myForm)
{
...
}

是否会分配更多内存来存储所有myForm数据,还是只保留对已分配myForm数据的位置的引用?

我担心的是,如果分配更多的内存来存储“附加”到myForm的所有内容,那么如果myForm是一个很大的形式,内存很快就会变满......

5 个答案:

答案 0 :(得分:12)

当您实例化原始表单时,表单对象将在堆上分配。当您调用myMethod时,您将按值传递引用类型(本质上是指向该对象的指针)。这意味着您传入的引用将被复制到myMethod的上下文中 - 这涉及32/64位堆栈分配,具体取决于您的体系结构。

因此,要回答您的问题,您的表单将不会被复制,但对其的引用将是。

免责声明:我很久没有使用过C#。

答案 1 :(得分:2)

从技术上讲,他们会创建引用的副本(所以另一个'引用大小的'内存分配),但引用的实际对象不会被复制和重新分配。

答案 2 :(得分:2)

没有。将Form引用传递给函数并不比传递整数贵。

Form是一个大对象(当你添加所有东西时可能是几十KB)。只有对它的引用才能作为参数传递。此引用仅为4个字节(在32位进程中),并在方法返回时消失。

答案 3 :(得分:1)

不,只分配了一个引用。

在C#中,引用类型的实例只能通过引用传递。也就是说,对象本身永远不会被复制,只有对它的引用 严格地说,当您将对象传递给方法时,其引用将按值传递。这意味着,您可以使用此引用访问该对象,并且您对该对象所做的更改将对调用您的方法的代码可见,但是,如果您将该接收的引用指向某个其他对象,则该更改不会影响给你原始引用的代码 - 因为引用是按值传递的。

与值类型相反,当按值传递时,会复制。

答案 4 :(得分:1)

表格是一个类。在C#中,一个类是一个引用类型 - 这意味着当它传递时它通过引用传递 。这基本上意味着Form实例所在的内存地址被传递到堆栈帧而不是复制所有字节。

如果方法参数是struct或类似int的基本类型,那么它将是值类型。值类型在传递给方法时,会将所有数据复制到方法的堆栈框架中。