一、核心概念(必背区分)
1. 非静态成员(实例成员)
无 static 修饰:字段、属性、方法
属于对象(实例)
每个对象拥有独立一份数据,对象之间互不干扰
必须new 对象后,通过对象名调用
2. 静态成员
有 static 修饰:静态字段、静态属性、静态方法
属于类,不属于对象
全局唯一、所有对象共享同一份数据
直接通过类名.成员调用,无需 new 对象
二、调用语法规则(固定死规则)
1. 非静态成员调用
必须实例化对象 →对象名.成员
People p1 = new People(); p1.F1(); p1.Id = 1;2. 静态成员调用
直接类名调用 →类名.成员
People.Age = 10; People.F2();三、静态与非静态 互相访问规则(超级高频考点)
1. 非静态方法 / 属性可以随意访问静态成员
非静态环境中,既能用非静态,也能用静态
public void F1() { // 允许访问静态属性、静态方法 Age = 10; F2(); }2. 静态方法 / 属性不能直接访问非静态成员
静态属于类,非静态属于对象,静态中没有当前对象
如果非要访问:必须手动 new 对象调用
public static void F2() { // 错误:直接调用非静态成员报错 // Id = 1; // F1(); // 正确:手动 new 对象访问 People p = new People(); p.F1(); p.Id = 1; }总结一句话规则
非静态可以随便碰静态
静态不能直接碰非静态
四、静态与非静态 数据存储区别(内存原理)
1. 非静态属性(独立数据)
每个对象拥有自己独立的数据,互不影响
People p1 = new People(); p1.AddNum(); // p1.Num = 1 People p2 = new People(); p2.AddNum(); // p2.Num = 1 // 两个对象Num互不干扰,都是1 Console.WriteLine(p1.GetNum()); //1 Console.WriteLine(p2.GetNum()); //12. 静态属性(共享数据)
所有对象共享同一份静态数据,一改全改
如果 Num 是静态属性:
p1.AddNum(); //静态Num=1 p2.AddNum(); //静态Num=2 // 全部共享同一个值 Console.WriteLine(p1.GetNum()); //2 Console.WriteLine(p2.GetNum()); //2五、超级易错坑点(笔试必坑)
1. 属性赋值死循环
禁止在属性set中给属性本身赋值
//错误写法:死循环 set { Id = value; } //正确写法:给字段赋值 set { id = value; }原因:Id=值会再次触发set访问器,无限递归 → 栈溢出
2. 静态无this
静态方法中不能使用this,因为this代表当前实例对象
3. 静态构造函数只执行一次
静态成员在程序生命周期内只初始化一次,全局共享
六、静态 VS 非静态 终极对比表
对比项 | 非静态成员 | 静态成员 |
|---|---|---|
修饰符 | 无 static | 有 static |
归属 | 对象(实例) | 类 |
调用方式 | 对象名.成员 | 类名.成员 |
数据特点 | 每个对象独立数据 | 所有对象共享同一份数据 |
互相访问 | 可直接访问静态 | 不可直接访问非静态 |
this关键字 | 可以使用 | 不可以使用 |
七、满分背诵口诀
static是静态,属于类,全局共享唯一数据
无static实例,属于对象,每个对象独立数据
非静可访静,静态不访非静
属性set只赋值给字段,千万别赋值给属性
静态类名点,非静对象点