static关键字:可以修饰成员、方法、代码块、静态内部类、静态导包。
1、修饰成员、方法、代码块,我们可以联想到它们在类初始化是的执行顺序,这里也可以把main主函数、构造函数、非静态代码块放在一起进行测试。
主函数的输出语句在实例化对象之前:静态代码块>静态方法/静态变量(这取决于在类中定义的顺序)>主函数输出>非静态代码块>构造函数。
demo测试:
public class String02 {
private static int i = 3;
private static int name(int i) {
return String02.i+i;
}
static {
System.out.println(\"静态代码块:\"+name(6));
}
String02() {
System.out.println(\"构造方法:\"+name(4));
}
{
System.out.println(\"非静态代码块:\"+name(5));
}
public static void main(String[] args) {
System.out.println(\"静态方法:\"+String02.name(1));
System.out.println(\"主函数运行\");
new String02();
}
}
测试结果:
静态代码块:9
静态方法:4
主函数运行
非静态代码块:8
构造方法:7
总结:静态代码块会随着类的加载而执行,而且只会执行一次。所以会率先执行静态代码块(如果该类继承了某类,并且所继承的类中也有静态代码块,会先执行父类的静态代码块,再执行子类的静态代码块),紧接着运行main方法,实例化对象,首先执行非静态方法,然后是构造函数。
其实在这还会延伸出一个问题,就是为什么main方法会是static的?
执行一个java程序的时候,因为java都是以类作为程序的组织单元,当我们要执行的时候,jvm并不知道这个main方法会放到哪个类当中,也不知道是否是要产生类的一个对象,为了解决程序的运行问题,所以将这个main方法定义为static。
2、静态内部类
静态内部类就是在内部类的基础上加上static关键字,静态内部类和普通内部类还是有区别的:
1)、静态内部类只能访问外部类的静态变量和静态方法,而普通内部类可以访问外部类的所有成员和方法;
2)、首先静态内部类不依赖外部类,直接就可以创建,即OutClass.InClass inCl = new OutClass.InClass(); 的方式就可以创建,而普通内部类需要先创建外部类的实例对象,通过外部类的实例对象创建,即 OutClass ou = new OutClass(); OutClass.InClass inCl = ou.new InClass();
3)、外部类访问内部类的成员时,通过内部类的引用间接的访问,而静态内部类直接通过类名. 的方式访问,因为静态内部类是属于类的。
内部类的使用,因为Java是单继承的,我们可以通过内部类的形式来间接的实现“多继承”(每个内部类都能独立地继承一个接口或者类,而无论外部类是否已经继承了某个接口或者类。因此,内部类使多重继承的解决方案变得更加完整),假设外部类继承A类,内部类继承B类,可以调用B类的某个方法,再方便外部类使用。
demo测试:
public class String02 {
public void name02() {
System.out.println(\"我是String02的name()方法\");
}
}
public class String03 {
public void name03() {
System.out.println(\"我是String03的name()方法\");
}
}
public class String04 extends String02{
//静态内部类
public static class S extends String03{}
public static void main(String[] args) {
String04.S s1 = new String04.S();
s1.name03();
}
}
输出结果:我是String03的name()方法
//总结:这样我们就可以在外部类String04不继承String03这个类的前提下,调用String043中的方法了。
这里就会延伸出一个问题,我们已知一个内部类的实例对象(OutClass.InClass in = new OutClass.InClass(); ),再不通过实例对象.成员方法(in.name())的方式来使用内部类的name()方法呢?这里就会涉及的Java反射的一些问题,class对象中method的反射,首先获取class对象,然后通过class对象获取Method对象,其次通过method对象的invoke()方法来操作指定类中的成员方法。
3.1)、获取class对象,三种方式
Class.forName(“类的全限定名,包含包名”)
类的实例对象.getClass()
类名.class (ClassA.class)
3.2)、method的反射应用
我们获取到class对象只够就可以得到该对象里面的信息了,包括成员方法、成员变量、构造函数等信息,这里我们获取成员方法,通过class对象中方法的反射来操作指定类的成员方法。在java.lang.reflec.Method中封装了对成员函数的信息,Method对象可以通过两种方式获取,getMethods()、getDeclaredMethods() ,前者获取的是所有public修饰的方法,包含继承父类的,后者获取的是自身声明的方法,包括私有的(private、protected、默认以及public)的方法,但不包含继承的方法。
我们通过方法的名称和参数列表可以唯一确定一个方法,getMethod(String name, Class<?>… parameterTypes);name——方法名,parameterTypes——参数列表,它的传入方式有两种方式,假设方法有两个string的形参,则String.class, String.class,若参数是一个String数组,则String[].class;如果没有形参的话,则参数列表为空。
3.3)、invoke( obj, … args);
第一个是 类型,也就是调用该方法的对象,第二个参数是一个可变参数类型,若方法的形参是一个string数组,则需要转换成 类型,( )String[]。
demo测试,这里只是简单做了个输出。
public class String04 extends String02{
//非静态内部类
public class S{
public void print(String [] sys) {
for (int i = 0; i < sys.length; i++) {
System.out.println(sys[i]);
}
}
}
//非静态内部类
public static class S1{
public void print(String [] sys) {
for (int i = 0; i < sys.length; i++) {
System.out.println(sys[i]);
}
}
}
public static void main(String[] args) {
//1、获取内部类的class对象
//1、1)、非静态内部类的对象需要依赖外部类的实例对象来创建
//1、2)、静态内部类可以直接通过外部类.内部类的方式创建
// String04 string04 = new String04();
// String04.S s1 = string04.new S();
String04.S1 s1 = new String04.S1();
Class<?> clazz = s1.getClass();
//2、获取method对象(首先根据方法名和参数列表确定将要操作的方法)
try {
Method method = clazz.getMethod(\"print\", String[].class);
//3、使用invoke()方法操作指定类的方法
//3、1)、invoke()其实是有返回值的,当方法如果没有返回值类型(void)则返回null,如果有返回值类型则返回对应的返回值类型(默认是 ,需要做强制类型转换)
String [] str = {\"q\",\"w\",\"e\"};
method.invoke(s1, ( )str);
} catch (Exception e) {
e.printStackTrace();
}
}
}
输出结果:
q
w
e
3、静态导包
3.1)静态导包是Java包的静音导入,在原有基础import Java.lang.String… 上添加了static关键字,这是JDK1.5的新特性,但是只限于操作静态方法,不能操作静态变量。
import static java.lang.Integer.*;
import static java.lang.System.out;
/**
* static关键字的静态导包应用
*
*/
public class String05 {
public static void main(String[] args) {
out.println(MAX_VALUE+\"&\"+MIN_VALUE);
out.println(toHexString(42));
}
}
输出结果:
2147483647&-2147483648
2a
这种静态导包的好处是简化了一些操作,但是建议在有很多重复调用的时候使用,如果仅有一到两次调用,不如直接写方便。
继续阅读与本文标签相同的文章
-
语音顶会Interspeech 论文解读|Investigation of Transformer based Spelling Correction Model for CTC-based End-to-End Mandarin Speech Recognition
2026-05-18栏目: 教程
-
阿里云“网红"运维工程师白金:做一个平凡的圆梦人 | 9月11号栖夜读
2026-05-18栏目: 教程
-
十位大师零距离,云栖大会通票+限量周边,还不够诱人吗亲? | 开发者必读(062期)
2026-05-18栏目: 教程
-
相同类中方法间调用时日志Aop失效处理
2026-05-18栏目: 教程
-
“2019密码应用高峰论坛”,探讨国密证书全生态应用
2026-05-18栏目: 教程
