You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

同一作用域内相同名称多次创建数组的内存地址变化问题

C#中两次执行new T[size]为同一数组变量赋值的内存行为说明

核心结论

  • 两次执行new T[size]赋值操作时,会触发全新的托管堆内存分配,数组变量arr存储的内存起始地址会发生变化
  • 不存在原地扩容的逻辑,原有数组的数据也不会自动拷贝到新分配的内存空间
  • 原数组内存如果没有其他引用指向,会被后续垃圾回收机制自动回收

原理说明

C#中数组属于引用类型:

  1. 局部数组变量arr本身存储在栈内存中,存储的实际内容是托管堆上数组对象的首地址
  2. 第一次执行arr = new byte[6]时,CLR会在托管堆上分配对应大小的内存,将该内存的首地址赋值给栈上的arr变量
  3. 第二次执行arr = new byte[10]时,CLR会重新在托管堆申请足够存储10个byte的全新内存块,将新的内存首地址覆盖到arr变量中,此时arr和原来的6长度数组没有任何关联

注意:你所说的「原地扩容、自动拷贝数据」是List<T>等封装集合的内部实现逻辑,原生数组的长度在创建后就是固定的,没有内置扩容能力,List<T>的扩容本质也是内部执行new T[newSize]再手动拷贝旧数据的逻辑,并不是真的原地扩容。

示例代码运行验证

你提供的代码本身就可以验证上述结论:

using System;
class HelloWorld
{
    static void Main ()
    {
        byte[] arr;
        arr = new byte[6];
        arr[2] = 6;
        Console.WriteLine ("len = {0}\n{1}", arr.Length, arr[2]);
        arr = new byte[10];
        arr[2] = 10;
        Console.WriteLine ("len = {0}\n{1}", arr.Length, arr[2]);
    }
}

运行输出如下:

len = 6
6
len = 10
10

从输出可以看到,第二次赋值后arr[2]没有保留第一次设置的6,说明并没有发生旧数据拷贝的操作,arr已经指向了全新的数组对象。

内容的提问来源于stack exchange,提问作者Abdullah

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.24 04:36:02