java-static关键字
Static关键字
从问题方面了解static关键字的使用:
问题一:为什么要使用static关键字?什么情况下才使用static关键字?
答:(1)一般情况,对象需要使用new来创建对象,数据存储空间才被分配,其类的变量或者方法供外界调用。
但上述方法,有两种情形是无法实现:
①只为某特定区域分配单一存储空间,但不考虑创建多少对象,甚至不创建对象;
②没有创建对象,也能调用该对象的方法。
而static关键字可以解决上面的情况。
(2)静态变量
静态变量的访问可以不创建对象, 直接用:“类名.静态变量”;也可以创建对象用 “对象名.静态变量” 访问静态变量。还可以通过改变“对象名.静态变量”来改变静态变量的值。
问:可以通过 “类名.静态变量” 访问静态变量,如:HelloWorld.className;也可以通过 “对象名.静态变量” 访问静态变量。但是,什么也不加,直接className也可以呀?是因为有什么弊端吗?
答:静态变量是可以直接引用的,不过是不安全的。在访问静态变量的时候首选是“类名.静态变量”的方式,这不仅是因为它强调了变量的static的结构,而且在某些情况下它还为编译器进行优化提供了更好的机会。
因为main()前也有一个static关键字,这表明mian()是一个静态方法,而静态方法是可以直接访问静态变量的。你所谓的直接className是在一个类里面才行的通,出了这个类就报错。

public class TestStatic { // static定义静态变量,保存班级名称 static String className = "JAVA开发一班"; public static void main(String[] args) { // 访问静态变量,输出班级名称 System.out.println(TestStatic.className); System.out.println(className); } }
特点:
1.静态成员变量是属于整个类的全局变量,它不单属于某一个对象;普通成员变量是属于类中的对象,它不能被所有对象共享。
2.静态成员变量必须在全局进行定义;而由于普通成员变量在创建一个对象的时候可以对它进行初始化,因此就不需要单独对它进行定义,只要声明即可。
3.静态成员变量在没有对象之前就存在。
1.static应用范围:可用于内部类、方法和变量。
2.标记一个方法为static,意味着这个方法,被所在类的所有实例公用,在类装载时被首先执行,执行一次即被所有该类的实例共享,同时意味着:
A、static方法内部不能引用非static变量。
B、static方法不能被子类重写为非static方法。
C、父类的非static方法不能被子类重写为static方法。
D、static代码块可以用static {}来完成,在类被第一次装载时执行初始化,先于静态方法和其他方法的执行。
3.标记一个变量为static,则该变量在内存中有不变的位置,相当于全局变量,所有类的实例都访问同一个存储变量区域。对其修改对于所有类的实例来说都是可见和一致的。
(3)静态方法
与静态变量一样,我们也可以使用static修饰方法,称为静态方法或类方法。其实之前我们一直写的 main 方法就是静态方法。
public class TestStaticMethod { //使用static关键字声明静态方法 public static void print(){ System.out.println("aaaaa"); } public static void main(String[] args) { //直接调用静态变量的类名.方法名,推荐方式 TestStaticMethod.print(); //也可以通过对象创建,来调用方法 TestStaticMethod t=new TestStaticMethod(); t.print(); } }
1.静态方法中可以直接调用同类中的静态成员,但不能直接调用非静态成员;
如果希望在静态方法中调用非静态变量,可以通过创建类的对象,然后通过对象来访问非静态变量。
2.在普通成员方法中,则可以直接访问同类的非静态变量和静态变量;
3.静态方法中不能直接调用非静态方法,需要通过对象来访问非静态方法。
public class TestStaticMethod { // static定义静态变量,保存班级名称 static String className = "JAVA开发一班"; String className2 = "JAVA开发二班"; //使用static关键字声明静态方法 public static void print(){ System.out.println("静态方法中可以直接调用静态变量(同类下):"+className); System.out.println("静态方法中可以直接调用静态变量:"+TestStaticMethod.className); //System.out.println("静态方法中不可以直接调用非静态变量:"+className2); //也可以通过对象创建,来调用方法 TestStaticMethod t=new TestStaticMethod(); System.out.println("静态方法中,可以先创建对象,再调用非静态变量:"+t.className2); } //非static关键字声明的方法,普通方法 public void show(){ System.out.println("普通方法中可以直接调用静态变量(同类下):"+className); System.out.println("普通方法中可以直接调用静态变量:"+TestStaticMethod.className); System.out.println("普通方法中可以直接调用非静态变量:"+className2); //也可以通过对象创建,来调用方法 TestStaticMethod t=new TestStaticMethod(); System.out.println("普通方法中,可以先创建对象,再调用非静态变量:"+t.className2); } public static void main(String[] args) { //直接调用静态变量的类名.方法名,推荐方式 TestStaticMethod.print(); //同类下,静态方法中可以直接调用静态方法 print(); //也可以通过对象创建,来调用方法 TestStaticMethod t=new TestStaticMethod(); t.print(); //但是普通方法,只能通过先创建对象来调用 t.show(); } }
(4)静态初始化块
在类的声明中,可以包含多个初始化块,当创建类的实例时,就会一次执行这些代码块,如果使用static 修饰初始化块,就称为静态初始化块。
注意:静态初始化块只在类加载时执行,且只会执行一次,同时静态初始化块只能给静态变量赋值,不能给初始化普通的成员变量。
程序运行时静态初始化块最先被执行,然后执行普通初始化块,最后才执行构造方法。
public class TestStatics { String name; // 声明变量name String sex; // 声明变量sex static int age;// 声明静态变量age // 构造方法 public TestStatics() { System.out.println("通过构造方法初始化name"); name = "tom"; } // 初始化块 { System.out.println("通过初始化块初始化sex"); sex = "男"; } // 静态初始化块 static { System.out.println("通过静态初始化块初始化age"); age = 20; } public void show() { System.out.println("姓名:" + name + ",性别:" + sex + ",年龄:" + age); } public static void main(String[] args) { // 创建对象 TestStatics hello = new TestStatics(); // 调用对象的show方法 hello.show(); /** * 通过静态初始化块初始化age * 通过初始化块初始化sex * 通过构造方法初始化name * 姓名:tom,性别:男,年龄:20 */ } }

浙公网安备 33010602011771号