12.3 静态成员与实例成员
静态成员会被所有对象共享同一空间。只要通过一个对象调用该成员,其他对象中的该成员的信息也会随之改变。
12.3.1 概念
- 每一个对象生成时,都会开辟自己的空间,包含自己的成员变量和成员方法等。
- 不同对象中同名的成员变量和方法,在各自对象空间中运行,各自独立,互不影响,叫作实例成员。
- 不同对象中同名的成员变量和方法,共享同一个空间,叫作静态成员。
- 静态成员独立于类的对象,先于对象的存在而存在。
- 无论创建了类的多少个对象,静态成员都只有一个实例空间。
- 在不同对象中的静态成员都是同一个空间,通过任一对象对该成员空间的访问都会影响其他成员。
静态成员与具体的对象无关,所以在Java中也称为类成员。可以使用静态成员进行对象之间消息的传递等。
12.3.2 静态变量——修饰符static
静态变量两种调用方式:
- 对象名.静态变量名
- 类名.静态变量名
12.3.3 静态方法
在定义成员方法时,在访问控制符后添加关键字static,就是静态方法。
静态方法也共享同一空间。
静态方法两种调用方式:
- 对象名.静态方法名()
- 类名.静态方法名()
成员方法的使用跟具体对象无关。
12.3.4 静态成员和实例成员之间的引用
1、静态成员和静态成员之间可以互相引用,
实例成员和实例成员之间也可以互相引用。
2、实例成员可以引用静态成员,但静态成员不可以引用实例成员。
原理:因为实例成员需要创建对象才能有其空间和值参与运行,而静态成员无须生成对象就已存在。
//Example1209.java
public class Example1209
{
public static int i = 1; //若写成public int i = 1;会报错
public static void main(String[] args)
{
System.out.println(i);
}
}
解释:静态方法main()不可引用非静态变量 i ,因为非静态变量 i 是跟随对象的生成才有空间运行。静态方法main()无须生成对象就已存在,运行时,i 还未生成。
12.3.5 应用实例
有了静态成员,我们可以省略生成对象这一步骤,直接用类名调用其成员。
试验:已知在Math类中有静态变量 PI 和静态方法 sqrt() 。求半径为30的圆的面积。另外有一个三角形,三边长分别为10、15、20,求面积。
//Example1210.java
public class Example1210
{
public static void main(String[] args)
{
int r = 30;
int a = 10, b = 15, c = 20;
System.out.println("圆的面积:");
System.out.println(Math.PI*r*r); //Math类中有静态变量PI,类名.PI就可以调用
System.out.println("三角形的面积:");
System.out.println("Math.sqrt((a+b+c)*(a+b-c)*(a+c-b)*(b+c-a))/4"); //Math类中有静态方法sqrt(),类名.sqrt()即可调用
}
}
问题:为什么变量 r, a, b, c 不用定义成static,即可在main()中调用
分析:不同于上一个程序,变量 i 定义在main()外面,main()要调用它,必须确保它已经生成。所以定义 i 为static,才能随着类的生成而生成,而不需要等待对象的生成。
本程序,变量 r, a, b, c 定义在main()里面,是main()中的局部变量,随着main()方法而生成,能够调用到。