Java中Static关键字之静态内部类和静态导包

static关键字可以说是真的很关键的关键字了,因为被static修饰的方法,变量,块,类都会在类加载的时候分配好了空间且一直存在。因此实现一种“全局”的概念,比如单例模式常用。

static关键字可用于方法、变量、代码块、类、包,方法变量和代码块我就不说了,本文主要说一下静态内部类和静态导包。

静态内部类

内部类

首先我们需要先看看什么是内部类。

我们说的内部类, 官方的叫法是嵌套类(Nested Classes), 嵌套类包括两种, 分别是静态嵌套类(Static Nested Classes)和内部类(Inner Classes), 其中内部类又有三种形式, 第一种就是我们常见的内部类, 其他两种特殊形式的内部类分别是局部类(Local Classes)和匿名类(Anonymous Classes).

首先内部类分成静态内部类和非静态内部类, 非静态内部类有额外两种特殊形式, 一种叫局部类, 另一种叫匿名内部类。

  1. 内部类可以访问外部类作用域内的数据,包括私有数据。
  2. 内部类可以对本包下的其他类隐藏起来。

静态内部类

静态内部类相当于外部类的静态属性,可以在无需实例化外部类的情况下直接使用className.的方式访问。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33

public class OutterClass {
public int normalInt=1;
public static int staticInt=2;
public static void doSomethingStatic(){
System.out.println("doSomethingStatic:"+staticInt);
}
public void doSomethingNormal(){
System.out.println("doSomethingNormal:"+normalInt);
}
public static class InnerStaticTest{
public int normalInt=3;
public static int staticInt=4;
public static void doSomethingStatic(){
OutterClass.doSomethingStatic();
System.out.println("doSomethingInnerStatic:"+OutterClass.staticInt+staticInt);
}
public void doSomethingNormal(){
System.out.println("doSomethingInnerNormal:"+normalInt);
}
}
public class InnerNormalTest{
public int normalInt=5;
public static final int staticInt=6;
// public static void doSomethingStatic(){
// System.out.println("doSomethingInnerStatic:"+OutterClass.staticInt+staticInt);
// }
public void doSomethingNormal(){
OutterClass.doSomethingStatic();
System.out.println("doSomethingInnerNormal:"+normalInt+staticInt+OutterClass.staticInt);
}
}
}

其中注释掉的为不可访问的。

作用(来自百度)

1)首先,用内部类是因为内部类与所在外部类有一定的关系,往往只有该外部类调用此内部类。所以没有必要专门用一个Java文件存放这个类。
2)静态都是用来修饰类的内部成员的。比如静态方法,静态成员变量,静态常量。它唯一的作用就是随着类的加载(而不是随着对象的产生)而产生,以致可以用类名+静态成员名直接获得。
这样静态内部类就可以理解了,因为这个类没有必要单独存放一个文件,它一般来说只被所在外部类使用。并且它可以直接被用 外部类名+内部类名 获得。

个人感觉,其实静态内部类相当于一个标注,比如B是A的内部静态类,调用是用A.B来调用,虽然其他类也可一访问,但是更多的是一种命名规范,对A来说,B是A的了,其他类最好不要调用。

静态导包

静态导包就是java包的静态导入,用import static代替import静态导入包是JDK1.5中的新特性。(很早了哈哈)
先来看一下实例。

1
2
3
4
5
6
import static java.lang.System.out;
public class Main {
static public void main(String[] args){
out.println("Hello World!");
}
}

我们再看一下,system的源码。(节选)

1
2
3
4
5
6
7
/**
* A handle to the standard output stream. Usually, this file
* descriptor is not used directly, but rather via the output stream
* known as {@code System.out}.
* @see java.lang.System#out
*/
public static final FileDescriptor out = standardStream(1);

其中out为静态变量。这样我们就可以清晰的再看这个结论,import static(顺序固定)是会引入一个静态成员,当然也可以用通配符.*来匹配该包下所有的静态成员。