In stasis, a thing exists, but in only one place, at one time. It is singular. A static
variable is tied to no class
instance. It occupies one location in memory.
Similarly, static
methods act on no instance data. They operate on static
data. They are often entry points. But we can create (or access) instances of classes inside them.
This program has 2 static
things. It has a static
field, named count, that is of type int
. Second it has the main()
entry point, which is where control flow begins.
Main
can access the count field because the field is static
. It uses the static
keyword.static
field can be accessed by both static
and instance methods. An instance field, however, cannot be accessed by static
methods.public class Program { static int count; public static void main(String[] args) { // Increment static variable. Program.count++; System.out.println(Program.count); // Repeat the increment. // ... The memory was not erased. Program.count++; System.out.println(Program.count); } }1 2
static
Consider this program. It has a static
int
and a non-static
int
in the Program
class
. We access the static
"size" with Program.size
.
Program
class
. It is tied to an instance, not the type.public class Program { static int size = 100; int code = 1000; public static void main(String[] args) { // Access static field with type name. System.out.println(Program.size); // Access instance field with instance. Program p = new Program(); System.out.println(p.code); } }100 1000
static
A final field cannot be changed in a program. A static
field, existing in only one place, can be changed. If you try to change a final field, a compiler error occurs.
static
—we can use static
fields and methods.public class Program { static int _id = 5; final int _code = 100; public static void main(String[] args) { _id++; // This is valid. _code++; // This fails. } }Exception in thread "main" java.lang.Error: Unresolved compilation problem: Cannot make a static reference to the non-static field _code
static
methodCompilers implement instance methods with an invisible first argument: the instance itself. I timed an instance method (getNumber
) and a static
one (getNumber2
).
static
method the same number of times in a nested loop.static
method calls were faster. They do not require the instance, so are simpler and faster.public class Program { int getNumber(int a) { // An instance method. return a * 2; } static int getNumber2(int a) { // A static method. return a * 2; } public static void main(String[] args) throws Exception { Program p = new Program(); long t1 = System.currentTimeMillis(); // Version 1: call instance method. for (int x = 0; x < 100; x++) { for (int i = 0; i < 10000000; i++) { if (p.getNumber(i) < 0) { throw new Exception(); } } } long t2 = System.currentTimeMillis(); // Version 2: call static method. for (int x = 0; x < 100; x++) { for (int i = 0; i < 10000000; i++) { if (Program.getNumber2(i) < 0) { throw new Exception(); } } } long t3 = System.currentTimeMillis(); // ... Times. System.out.println(t2 - t1); System.out.println(t3 - t2); } }955 ms, int getNumber() [Instance] 880 ms, static int getNumber2() [Static]
static
fieldsIn my test, a static
field is slower to access than an instance (class
-based) field. The time increase is consistently measurable.
Program
class
many times.static
field on the Program
class
—we do not use a Program
reference to access the field.static
field. Using instance-based fields is faster.public class Program { int field1 = 100; static int field2 = 100; public static void main(String[] args) throws Exception { Program p = new Program(); long t1 = System.currentTimeMillis(); // Version 1: use instance field. for (int x = 0; x < 100; x++) { for (int i = 0; i < 10000000; i++) { if (p.field1 * 2 <= 199) { throw new Exception(); } } } long t2 = System.currentTimeMillis(); // Version 2: use static field. for (int x = 0; x < 100; x++) { for (int i = 0; i < 10000000; i++) { if (Program.field2 * 2 <= 199) { throw new Exception(); } } } long t3 = System.currentTimeMillis(); // ... Times. System.out.println(t2 - t1); System.out.println(t3 - t2); } }763 ms, field1 [Instance field] 953 ms, field2 [Static field]
To a compiler, instance methods are often static
ones with a hidden first argument—the instance reference. Static methods can receive class
arguments.
static
and instance method is clarity of syntax. It is easier to decide what an instance method does.We achieve speed increases with static
methods. But if those methods use excessive static
fields, we lose our optimization. A delicate balance is needed for optimal speed.
Static methods and fields are used throughout Java programs. The main()
method, used in every program, is itself a static
method.