Java学习笔记四:static关键字

1.static表示什么?

static表示“全局”或者“静态”的意思。在Java中没有全局变量的概念,static 可以简单的理解为全局的,独立的一个功能。

(1)当我们在使用 static 修饰成员变量或者成员方法的时候,通常会在Java内存中为这些变量或者方法指定了一块独立的区域(这块区域可能在栈中,也有可能在堆中)。

(2)如果静态的变量或方法在不出其作用域的情况下,其 引用句柄是不会发生改变的。

(3)这块区域是内存共享的,它的引用都指向同一个位置,就是说如果我们修改引用指向的的值,这个值就被改变了;当其他对象使用这个值时,就是修改后的值。

代码:

public class Lesson_02_Static
{
    public static int staticFiled = 0;
    public int notStaticFiled = 0;
    
    static
    {
        int staticBolckFiled = 0;
    }
    
    public Lesson_02_Static()
    {
        staticFiled++;
        notStaticFiled++;
    }
    
    public void print()
    {
        System.out.println("StaticFiled:" + staticFiled + ", NotStaticFiled:" + notStaticFiled);
    }
    
    public static void main(String[] args)
    {
        Lesson_02_Static ls1 = new Lesson_02_Static();
        ls1.print();
        
        Lesson_02_Static ls2 = new Lesson_02_Static();
        ls2.print();
    }
}

输出结果:

StaticFiled:1, NotStaticFiled:1
StaticFiled:2, NotStaticFiled:1

 

它不依赖类特定的实例,被类的所有实例共享。只要这个类被加载,Java虚拟机就能根据类名在运行时数据区的方法区内定找到他们。

因此,static对象可以在它的任何对象创建之前访问,无需引用任何对象

 

2.static使用场景?

1.修饰静态变量(注意:不能是局部变量)。如:

public static int staticFiled = 0;

说明:

静态变量:被static修饰的变量,在内存中只有一份,在加载类的过程中完成静态变量的内存分配,不会随着类的实例化和增加。

实例变量:被static修饰的变量,当实例化类时,可以在内存中存在多个拷贝。

 

2.静态方法。如:

public static void main(String[] args)
    {
        Lesson_02_Static ls1 = new Lesson_02_Static();
        ls1.print();
        
        Lesson_02_Static ls2 = new Lesson_02_Static();
        ls2.print();
    }

说明:

(1)静态方法中不能用this和super关键字,不能直接访问所属类的实例变量和实例方法。

静态方法中调用非静态方法提示错误,编译不通过;

非静态方法可以调用静态方法。

(2)因为static方法独立于任何实例,因此static方法必须被实现,而不能是抽象的abstract。

 

3.静态块。如:

static
    {
        int staticBolckFiled = 0;
    }

说明:

静态块位置可以随意放置,初始化顺序时不会随着位置变化而变化。一般情况下,会放在成员变量结束,类方法的开始的地方,方便理解。

 

3.static初始化

(1)初始化顺序是从类的开始到结尾查找static块,并且比类自身构造函数要早。

class StaticInit
{
    public static int staticFiled = 0;
    public int notStaticFiled = 0;
    
    static
    {
        System.out.println("First Init");
    }
    
    public StaticInit()
    {
        System.out.println("structure Init");
    }
    
    public static void main(String[] args)
    {
        new StaticInit();
    }
    
    static
    {
        System.out.println("Second Init");
    }
}

输出结果:

First Init
Second Init
structure Init

(2)static变量的初始化仅能一次

class StaticInt2
{
    T1 t1 = new T1(2);
    
    T1 t3 = new T1(4);
    
    T1 t2 = new T1(3);
    
    public StaticInt2()
    {
        System.out.println("t1: " + t1.t);
        System.out.println("t2: " + t2.t);
        System.out.println("t3: " + t3.t);
    }
    
    public static void main(String args[])
    {
        new StaticInt2();
    }
}

class T1
{
    static int t = 1;
    
    T1(int b)
    {
        t = b;
    }
}

输出结果:

t1: 3
t2: 3
t3: 3

t的值在最后被设置为3,说明静态变量不会根据new 实例化而初始化(即不会在new时初始化值1).

说明:

在实际debug过程中,静态块中的方法先执行,然后在执行构造函数,最后执行成员变量的初始化。

 

总结:

static 指定的是一个固定的位置,在内存中只有一份;

在初始化时,优先执行static块。

posted on 2014-09-27 20:18  winlrou  阅读(197)  评论(0编辑  收藏  举报