C#学习笔记 -- 变量、内存
1、变量在内存中分配空间
以变量名对应的内存地址为起点, 以其数据类型所要求的存储空间为长度的一块内存区域
(1)值变量如何存储在内存上
-
内存在计算机中被分成了一个字节一个字节的区域, 其中每个8个bit构成一个字节, 每个字节有自己唯一标识
-
操作系统会预留一部分内存, 别的进程无法使用 用橙色表示
-
别的进程也会占用内存, 当前进程无法使用 ,用黄色表示
假设
short var = 1000;
-
short : -2^15 - 2^15 - 1 在内存中占16个bit 其中, 最高位字节内存地址的第一个bit位代表符号
-
dec 1000 = bin 0011 1110 1000, 有12个bit, 不满16位 向前补0 => 0000 0011 1110 1000
-
不带负号, 按高位到低位内存地址存储 1110 1000 0000 0011
short var = -1000;
-
带负号, 取反 + 1 => 0变1, 1变0 最后 + 1
-
按高位到低位存储 0001 1000 1111 1100
(2)引用类型如何存储到内存
声明并初始化引用类型地址的值, 内存会给你分配一个四个字节的空间, 这块空间上全部都是0, 用于存储该对象在堆中真实存储位置所在内存地址的值
(3)不同类型变量在内存上的不同位置
-
局部方法中任何局部变量存储在栈里, 包括值类型 引用类型
-
引用类型的真实地址在堆里
-
引用类型所对应类实例化后其中的值变量在堆里
2、变量默认值
-
成员变量: 如果声明成员变量, 但是没有进行初始化, 但是类实例化了,
-
对于值类型, 这个成员变量默认值为0,
-
-
局部变量: 必须赋值, 不给赋值报错
3、常量 const
-
使用const 修饰的值变量, 变成常量, 不能更改
const int var = 1;
-
常量必须初始化
4、装箱 拆箱
(1)装箱
static void Main(string[] args)
{
int x = 100;
object obj;
obj = x;
}
-
当你声明一个引用类型变量, 没初始化, 在内存上, 给这个变量分配的是四个字节的0, 也就是没有指向真实对象存储地址,
-
那么如果这个引用指向值类型变量, 可能让这个引用变量, 直接指向了某个地址, 这个内存地址可能是操作系统专属区域, 操作系统就垮了
-
装箱操作, 就是一个引用变量, 所引用的内存地址, 不是存在堆里的实例, 而是某个值类型, 并且指向内存地址的时候, 则在堆上找一块空间, 赋予这个值类型, 并且让引用变量指向这块内存地址
-
会损失性能
(2)拆箱
-
把堆上object类型的值, 转为目标值类型, 存储到栈中
-
会损失性能
static void Main(string[] args)
{
int x = 100;
object obj;
obj = x;
x = (int)obj;
}