一、在程序运行时由CLR管理内存分配(Memory Allocation),程序启动时,操作系统会为每一个线程申请一个独立的栈内存,用于存储方法的局部变量、参数和返回值等;CLR会为进程申请一个连续的内存空间作为托管堆内存,用于存储引用类型对象和类型对象等;

  1.托管堆主要包含两部分:存储引用类型对象的GC堆(GC Heap)和存储类型对象的加载堆(Loader Heap),其中GC堆分为小对象堆(Small Object Heap,SOH,<85000byte的对象)和大对象堆(Larage Object Heap,LOG,>=85000byte的对象);加载堆不受GC控制,生命周期从创建到应用程序域被卸载;
  2.CLR在申请托管堆内存时,会维护一个指向下一个对象内存地址的指针,当在托管堆中分配新对象时,会通过该指针添加值来为对象分配所需的内存,因此在托管堆中分配内存和在栈内存中分配内存的速度基本一样快;

  二、在栈上分配值类型的变量时,如果值类型所占的空间不足当前系统的位数时,会分配当前系统位数的内存空间,例如在64位系统上分配的int类型的变量占用64位,即8个字节;对于引用类型地址也是这样,即32位系统上引用类型地址占用4个字节,64位系统上则占用8个字节;

//在64位系统上测试:
unsafe
{
int num1 = ;
int num2 = ;
MyClass myClass = new MyClass();
int num3 = ;
Console.WriteLine((int)&num1);
Console.WriteLine((int)&num2); //与num1地址相差8个字节
Console.WriteLine((int)&num3); //与num2地址相差16个字节
}

  

  三、在使用运算符new创建引用类型对象或装箱操作等在托管堆上创建对象时,CLR所做的主要操作有:

  1.计算类及所有基类中声明的所有实例字段所需要的字节数,还有两个开销成员(Overhead Member)的字节数:同步块索引(Sync Block Index)和类型对象指针(Type Object Pointer);
※同步块索引为线程同步提供支持,也被称为对象头字节(Object Header Word);
※类型对象指针存储该对象的类型对象所在的内存地址,也被称为方法表指针(Method Table Pointer);
  2.从托管堆中分配计算所得到的字节数,所有字节初始化为0;
  3.初始化对象的类型对象指针和同步块索引;
  4.调用对应的实例构造函数,初始化实例字段,执行自定义构造函数中的其它操作;
※优先调用直接基类中的实例构造函数,直接基类中的实例构造函数又会调用其直接基类中的实例构造函数,最终最先调用的是基类System.Object中的实例构造函数;
  5.返回新建对象的引用;

  注:32位系统中,同步块索引和类型对象指针分别占4个字节,占用的总空间大小会进行4字节倍数的对齐,同时即使类型定义中没有实例字段,也会至少占用4个字节,即最小占用内存空间12字节;
  注:64位系统中,同步块索引和类型对象指针分别占8个字节,占用的总空间大小会进行8字节倍数的对齐,同时即使类型定义中没有实例字段,也会至少占用8个字节,即最小占用内存空间24字节;

  注:CLR在托管堆中连续分配多个对象时,这些对象在内存中也是连续存储的;

  注:可以使用WinDbg查看具体的内存分配情况;

  注:CLR高度优化了托管堆上内存的分配和释放,大多数情况下,在堆内存上分配类实例与在栈内存上分配结构实例的性能并无显著差异;


如果您觉得阅读本文对您有帮助,请点一下“推荐”按钮,您的认可是我写作的最大动力!

作者:Minotauros
出处:https://www.cnblogs.com/minotauros/

本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。

C#自动内存分配的更多相关文章

  1. 《深入理解Java虚拟机》-----第3章 垃圾收集器与内存分配策略

    Java与C++之间有一堵由内存动态分配和垃圾收集技术所围成的“高墙”,墙外面的人想进去,墙里面的人却想出来. 3.1 概述 说起垃圾收集(Garbage Collection,GC),大部分人都把这 ...

  2. 自动内存管理算法 —— 标记和复制法

    最近阅读了<垃圾回收算法手册>这本经典的书籍,借此机会打算写几篇内存管理算法方面的文章,也算是自己的总结吧.                                         ...

  3. Java自动内存管理机制学习(二):垃圾回收器与内存分配策略

    备注:本文引自<深入理解Java虚拟机第二版>仅供参考 图片来自:http://csdn.net/WSYW126 垃圾收集器与内存分配策略 概述 GC要完成3件事: 哪些内存需要回收? 什 ...

  4. 【深入理解JAVA虚拟机】第二部分.内存自动管理机制.3.垃圾收集器与内存分配策略

    1.学习目的 当需要排查各种内存溢出. 内存泄漏问题时,当垃圾收集成为系统达到更高并发量的瓶颈时,我们就需要对这些“自动化”的技术实施必要的监控和调节. Java内存运行时区域的各个部分,其中程序计数 ...

  5. C语言内存分配方法。

    当C程序运行在操作系统上时,操作系统会给每一个程序分配一定的栈空间. 堆为所有程序共有的,需要时需要申请访问. 一.栈 局部变量.函数一般在栈空间中. 运行时自动分配&自动回收:栈是自动管理的 ...

  6. 小白请教几个关于Java虚拟机内存分配策略的问题

    最近在看周志明所著的<深入理解Java虚拟机>,有几个问题不太明白,希望对虚拟机有研究的哥们儿帮我解答一下.先说一下我进行试验的环境: 操作系统:Mac OS X 10.11.6 EI C ...

  7. java中内存分配策略及堆和栈的比较

    Java把内存分成两种,一种叫做栈内存,一种叫做堆内存 在函数中定义的一些基本类型的变量和对象的引用变量都是在函数的栈内存中分配.当在一段代码块中定义一个变量时,java就在栈中为这个变量分配内存空间 ...

  8. C语言内存分配

      (1)代码区(text segment).存放CPU执行的机器指令(machine instructions).通常,代码区是可共享的 (即另外的执行程序可以调用它),因为对于频繁被执行的程序,只 ...

  9. C标准库-数值字符串转换与内存分配函数

    原文链接:http://www.orlion.ga/977/ 一.数值字符串转换函数 #include <stdlib.h> int atoi(const char *nptr); dou ...

随机推荐

  1. Thinkphp5.0 的Model模型

    Thinkphp5.0 的Model模型 新建user模型User.php: <?php namespace app\index\model; use think\Model; class Us ...

  2. 【进击后端】linux安装最新版nodejs

    nodejs下载:https://nodejs.org/zh-cn/download/ 1.cd /root/download 2.wget https://nodejs.org/dist/v6.11 ...

  3. 【进击后端】Ubuntu 命令行 安装nginx

    一.安装nginx apt-get install nginx 安装路径为:/etc/nginx/conf.d 二.配置nginx,在conf.d目录下新建test.conf 新建文件的命令是vi t ...

  4. Swap Nodes in Pairs(链表操作)

    Given a linked list, swap every two adjacent nodes and return its head. For example,Given 1->2-&g ...

  5. maven项目互相dependcy依赖问题

    1.自己编写的maven项目,在编译后,也会在.m2文件夹下生成jar包,可以供第三方引用使用. 2.比如几个项目互相依赖对方的jar包,就要首先选择编译哪个jar包,编译完成后生成jar,再编译依赖 ...

  6. 网易互娱2017实习生招聘游戏研发工程师在线笔试第二场 C

    偶尔碰到这题,简单数位DP题,然而我已生疏了…… 这次算是重新想到的,看来对DP的理解有增进了…… dp[i][j][k],表示前i为,mod为j,是否出现2.3.5的剩下的数位可组成的数字.答案就是 ...

  7. UVa 10534 Wavio Sequence (最长递增子序列 DP 二分)

    Wavio Sequence  Wavio is a sequence of integers. It has some interesting properties. ·  Wavio is of ...

  8. StringBuffer疑问

    为何结果为AB.B? public static void main(String[] args) { StringBuffer a=new StringBuffer("A"); ...

  9. PHP数组去空项

    $strDelCodes = "A;B;;C;;C;D;;;D;D";$rsArray = array_values (array_unique (array_diff (spli ...

  10. VBS 操作Word

    VBS 操作Word   1.新建Word文档 '使用Add方法 Dim ObjWD,ObjDOC Set ObjWD=CreateObject("Word.application" ...