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

Phi*_*ong 97 java static reference

我被告知了几个定义,在维基百科上看,但作为Java的初学者,我仍然不确定它的含义.有流利的Java和白痴吗?

ink*_*dmn 242

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

public class Foo {
    public static void doStuff(){
        // does stuff
    }
}
Run Code Online (Sandbox Code Playgroud)

所以,而不是创建一个Foo实例,然后doStuff像这样调用:

Foo f = new Foo();
f.doStuff();
Run Code Online (Sandbox Code Playgroud)

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

Foo.doStuff();
Run Code Online (Sandbox Code Playgroud)

  • 还应该提到的是,静态字段由类的所有实例共享,因此所有实例都看到相同的值. (18认同)
  • @Peter:它并不是"由所有实例共享",因为它只属于其中一个,因为它属于类.某些"公共静态"对每个人来说都是免费的,而不仅仅是在实例之间共享. (9认同)
  • 那讲得通!谢谢. (5认同)
  • 静态方法在概念上类似于Python和C++等语言中的所谓自由函数.只是函数名称的范围是在类名中. (2认同)

Bos*_*one 37

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


Pac*_*ace 16

静态关键字可以在Java中几种不同的方式被使用并且在几乎所有的情况下,它是一种改性剂,这意味着它在修改的事情是不的包围对象实例可用.

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

public class SomeObject {
    public int someField;
    public void someMethod() { };
    public Class SomeInnerClass { };
}
Run Code Online (Sandbox Code Playgroud)

为了使用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();
    }
}
Run Code Online (Sandbox Code Playgroud)

如果我将这些东西声明为静态,那么它们不需要封闭的实例.

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();
    }
}
Run Code Online (Sandbox Code Playgroud)

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

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

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
    }
}
Run Code Online (Sandbox Code Playgroud)

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

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
        }

    }
}
Run Code Online (Sandbox Code Playgroud)

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

public class SomeObject {
    public static interface SomeInterface { };
    public static @interface SomeAnnotation { };
    public static enum SomeEnum { };
}
Run Code Online (Sandbox Code Playgroud)

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

这只是描述了他们关键字的作用.它没有描述关键字的使用是否是一个坏主意.在其他问题中可以更详细地讨论这一点,例如使用大量静态方法是一件坏事吗?

关键字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
    }
}
Run Code Online (Sandbox Code Playgroud)

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

public class SomeObject {

    private static int x;

    static {
        x = 7;
    }
}
Run Code Online (Sandbox Code Playgroud)


mel*_*ngs 7

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