用外行人的话来说,Java中“静态”意味着什么?

时间:2010-04-15 21:47:33

标签: java static reference

我被告知了几个定义,在维基百科上看,但作为Java的初学者,我仍然不确定它的含义。任何人都能说流利的Java和白痴?

6 个答案:

答案 0 :(得分:234)

static表示标记为此类的变量或方法在类级别可用。换句话说,您不需要创建类的实例来访问它。

public class Foo {
    public static void doStuff(){
        // does stuff
    }
}

因此,不是创建一个Foo实例,而是像这样调用doStuff

Foo f = new Foo();
f.doStuff();

您只需直接针对类调用该方法,如下所示:

Foo.doStuff();

答案 1 :(得分:37)

非常外行,这个类是模具,对象是用该模具制作的副本。静态属于模具,可以直接访问而无需进行任何复制,因此上面的示例

答案 2 :(得分:14)

静态关键字可以在Java中以多种不同的方式使用,几乎在所有情况下都是一个修饰符,这意味着它正在修改的东西可以在没有封闭对象实例的情况下使用

Java是一种面向对象的语言,默认情况下,您编写的大多数代码都需要使用该对象的实例。

public class SomeObject {
    public int someField;
    public void someMethod() { };
    public Class SomeInnerClass { };
}

为了使用someField,someMethod或SomeInnerClass ,我必须首先创建SomeObject的实例

public class SomeOtherObject {
    public void doSomeStuff() {
        SomeObject anInstance = new SomeObject();
        anInstance.someField = 7;
        anInstance.someMethod();
        //Non-static inner classes are usually not created outside of the
        //class instance so you don't normally see this syntax
        SomeInnerClass blah = anInstance.new SomeInnerClass();
    }
}

如果我将这些内容声明为静态,那么不需要封闭的实例

public class SomeObjectWithStaticStuff {
    public static int someField;
    public static void someMethod() { };
    public static Class SomeInnerClass { };
}

public class SomeOtherObject {
    public void doSomeStuff() {
        SomeObjectWithStaticStuff.someField = 7;
        SomeObjectWithStaticStuff.someMethod();
        SomeObjectWithStaticStuff.SomeInnerClass blah = new SomeObjectWithStaticStuff.SomeInnerClass();
        //Or you can also do this if your imports are correct
        SomeInnerClass blah2 = new SomeInnerClass();
    }
}

声明静态的东西有几个含义。

首先,在整个应用程序中只能有一个静态字段值

public class SomeOtherObject {
    public void doSomeStuff() {
        //Two objects, two different values
        SomeObject instanceOne = new SomeObject();
        SomeObject instanceTwo = new SomeObject();
        instanceOne.someField = 7;
        instanceTwo.someField = 10;
        //Static object, only ever one value
        SomeObjectWithStaticStuff.someField = 7;
        SomeObjectWithStaticStuff.someField = 10; //Redefines the above set
    }
}

第二个问题是静态方法和内部类不能访问封闭对象中的字段(因为它没有一个)。

public class SomeObjectWithStaticStuff {
    private int nonStaticField;
    private void nonStaticMethod() { };

    public static void someStaticMethod() {
        nonStaticField = 7; //Not allowed
        this.nonStaticField = 7; //Not allowed, can never use *this* in static
        nonStaticMethod(); //Not allowed
        super.someSuperMethod(); //Not allowed, can never use *super* in static
    }

    public static class SomeStaticInnerClass {

        public void doStuff() {
            someStaticField = 7; //Not allowed
            nonStaticMethod(); //Not allowed
            someStaticMethod(); //This is ok
        }

    }
}

static关键字也可以应用于内部接口,注释和枚举。

public class SomeObject {
    public static interface SomeInterface { };
    public static @interface SomeAnnotation { };
    public static enum SomeEnum { };
}

在所有这些情况下,关键字都是多余的,无效。默认情况下,接口,注释和枚举是静态的,因为它们永远不会与内部类建立关系。

这只描述了他们关键字的作用。它没有描述关键字的使用是否是一个坏主意。在Is using a lot of static methods a bad thing?

等其他问题中可以更详细地介绍这一点

关键字static也有一些不太常见的用法。有静态导入允许您使用不合格的静态类型(包括非冗余标记为静态的接口,注释和枚举)。

//SomeStaticThing.java
public class SomeStaticThing {
    public static int StaticCounterOne = 0;
}

//SomeOtherStaticThing.java
public class SomeOtherStaticThing {
    public static int StaticCounterTwo = 0;
}

//SomeOtherClass.java
import static some.package.SomeStaticThing.*;
import some.package.SomeOtherStaticThing.*;

public class SomeOtherClass {
    public void doStuff() {
        StaticCounterOne++; //Ok
        StaticCounterTwo++; //Not ok
        SomeOtherStaticThing.StaticCounterTwo++; //Ok
    }
}

最后,有一些静态初始化程序,它们是在第一次加载类时运行的代码块(在应用程序中第一次实例化类之前通常)和(像静态方法一样)无法访问非静态字段或方法。

public class SomeObject {

    private static int x;

    static {
        x = 7;
    }
}

答案 3 :(得分:7)

当您想要应用 Singleton 设计模式时,使用静态属性和操作时的另一个很好的示例。简而言之,Singleton设计模式确保在系统的生命周期内构建特定类的一个且仅一个对象。为确保只构造一个对象,Singleton模式的典型实现保留对单个允许对象实例的内部静态引用,并使用static操作控制对该实例的访问

答案 4 :(得分:3)

除了@inkedmn指出的内容外,静态成员还在类级别。因此,所述成员由JVM一次为该类加载到内存中(当加载类时)。也就是说,没有为其所属的类的 n 实例加载静态成员的 n 个实例。

答案 5 :(得分:-4)

以上几点是正确的,我想补充一些关于Static关键字的重点。

在内部使用静态关键字时发生的事情是它将存储在永久内存(即堆内存)中,我们知道有两种类型的内存它们是堆栈内存(临时内存)和堆内存(永久内存),所以如果你不使用静态关键字,那么它将存储在堆栈内存(或者您可以将其称为易失性内存)。

所以你会怀疑这个权利有什么用?

示例:static int a = 10;(1个程序)

刚才我告诉你,如果你对变量使用静态关键字,或者对于方法,它会存储在永久性内存中。

所以我在其他具有不同价值的程序中使用关键字 static 声明了相同的变量。

示例:static int a = 20;(2个程序)

变量'a'由程序1 存储在堆内存中。当时程序2 中找到相同的静态变量'a'不会再次在堆内存中创建'a'变量,而只是将a的值替换为10到20

一般情况下,如果你不会将'a'声明为静态变量,它会在堆栈内存(临时内存)中创建再次变量'a'。

总的来说,我可以说,如果我们使用静态关键字
我们可以节省记忆 我们可以避免重复 3.无需在类名的帮助下按顺序创建对象以访问静态变量,您可以访问它。