Introduction to Static Variables and Methods
The static keyword in Java is a modifier that makes a member of a class independent of the instances of that class. In other words, the static modifier is used to define variables and methods related to the class as a whole, rather than to an instance (object) of the class. Hence, static variables are often called class variables, while static methods are commonly referred to as class methods. Class variables and methods are stored in fixed locations in memory and are accessed without a reference to an object, directly through the class name itself [1].
A common use for static methods is to access static variables. However, not all combinations of instance and class variables and methods are allowed. Namely, static methods can only use static variables and call static methods—they cannot access instance variables or methods directly, without an object reference. This is because instance variables and methods are always tied to a specific instance, i.e., object of their class.
Due to their instance-less nature, static variables and methods are sometimes used to construct stateless utility classes [2].
 
Non-static Variable X Cannot be Referenced from a Static Context & Non-static Method X Cannot be Referenced from a Static Context
A static variable is initialized once, when its class is loaded into memory, and its value is shared among all instances of that class. On the other hand, a non-static variable is initialized every time a new instance of its class is created, and as such there can be multiple copies of it in memory, each with a different value. Consequently, attempting to access a non-static variable from a static context (a static method or block) without a class instance creates ambiguity—every instantiated object has its own variable, so the compiler is unable to tell which value is being referenced. And if no class instance is created, the non-static variable is never initialized and there is no value to reference. For the same reasons, a non-static method cannot be referenced from a static context, either, as the compiler cannot tell which particular object the non-static member belongs to.
To prevent this conundrum when accessing instance variables and methods from a static context, the Java compiler raises the non-static variable X cannot be referenced from a static context,
or the non-static method X cannot be referenced from a static context
error, respectively. To rectify this problem, there are two possible solutions:
- refer to the non-static member through a class instance, or
- declare the non-static member static.
 
Examples
Non-static Variable X Cannot be Referenced from a Static Context
The code example in Fig. 1(a) shows how attempting to increment and print the value of the non-static variable count
from the static main
method results in the non-static variable count cannot be referenced from a static context
error. The Java compiler flags both attempts to reference the instance variable without an actual class instance and points to their exact location in the source code.
Creating a local class instance in the main
method and accessing the count
variable through this object resolves this issue (Fig. 1(b)), as it unambiguously links the variable to a specific object. In scenarios where the variable in question doesn’t need to hold data specific to a class instance, but can either be shared among all class instances or used independently of any, adding the static
modifier to it makes it accessible from a static context, effectively resolving the error, as shown in Fig. 1(c).
(a)
1
2
3
4
5
6
7
8
9
10
11
package rollbar;
public class StaticContextVariable {
private int count = 0;
public static void main(String... args) {
count++;
System.out.println(count);
}
}
StaticContextVariable.java:8: error: non-static variable count cannot be referenced from a static context
count++;
^
StaticContextVariable.java:9: error: non-static variable count cannot be referenced from a static context
System.out.println(count);
^
2 errors
(b)
1
2
3
4
5
6
7
8
9
10
11
12
package rollbar;
public class StaticContextVariable {
private int count = 0;
public static void main(String... args) {
var classInstance = new StaticContextVariable();
classInstance.count++;
System.out.println(classInstance.count);
}
}
1
(c)
1
2
3
4
5
6
7
8
9
10
11
package rollbar;
public class StaticContextVariable {
private static int count = 0;
public static void main(String... args) {
StaticContextVariable.count++;
System.out.println(StaticContextVariable.count);
}
}
1
 
Non-static Method X Cannot be Referenced from a Static Context
Just like non-static variables, non-static methods need an object in order to be instantiated into memory and referenced. Fig. 2(a) shows how trying to access the instance method incrementAndGetCount()
without a class instance raises the non-static method incrementAndGetCount() cannot be referenced from a static context
error.
Creating a class instance and calling this method on it, as demonstrated in Fig. 2(b), fixes the error. Making the incrementAndGetCount()
method static and referencing it via the class itself (lines 7 and 12 in Fig. 2(c)) also mediates this problem, as there is no longer the need for an object to exist before the method can be invoked.
(a)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
package rollbar;
public class StaticContextMethod {
private static int count = 0;
private int incrementAndGetCount() {
return ++count;
}
public static void main(String... args) {
System.out.println(incrementAndGetCount());
}
}
StaticContextMethod.java:12: error: non-static method incrementAndGetCount() cannot be referenced from a static context
System.out.println(incrementAndGetCount());
(b)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
package rollbar;
public class StaticContextMethod {
private static int count = 0;
private int incrementAndGetCount() {
return ++count;
}
public static void main(String... args) {
var classInstance = new StaticContextMethod();
System.out.println(classInstance.incrementAndGetCount());
}
}
1
(c)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
package rollbar;
public class StaticContextMethod {
private static int count = 0;
private static int incrementAndGetCount() {
return ++count;
}
public static void main(String... args) {
System.out.println(StaticContextMethod.incrementAndGetCount());
}
}
1
 
Summary
Static variables and methods, jointly known as static class members in Java, are used to model data and behavior common to all instances of a class, or in some cases to store data and procedures for stateless classes which don’t need to be instantiated. Contrary to this, non-static variables and methods depend on class instances, as they store and manipulate data specific to individual objects. Therefore, non-static members cannot be accessed from a static context, i.e., there has to be a class instance that references these members. Failing to abide by this rule inevitably produces the non-static variable X cannot be referenced from a static context
or the non-static method X cannot be referenced from a static context
compile-time error, depending on whether it’s a variable or a method that is being referenced. The error message generated by the Java compiler contains the exact location of the variable or method in question, and resolving the issue involves making use of a new or an existing class instance, or alternatively making the class member static where appropriate.
 
Track, Analyze and Manage Errors With Rollbar
Managing errors and exceptions in your code is challenging. It can make deploying production code an unnerving experience. Being able to track, analyze, and manage errors in real-time can help you to proceed with more confidence. Rollbar automates error monitoring and triaging, making fixing Java errors easier than ever. Sign Up Today!
 
References
[1] Oracle, 2021. Understanding Class Members (The Java™ Tutorials > Learning the Java Language > Classes and Objects), Oracle and/or its affiliates. [Online]. Available: https://docs.oracle.com/javase/tutorial/java/javaOO/classvars.html. [Accessed: Dec. 08, 2021]
[2] Y. Taz, 2019. Writing a Utility Class for Collections in Java 8, Yavuz Tas. [Online]. Available: https://yavuztas.dev/java/collections/streams/2019/08/10/java8-utility-class.html. [Accessed: Dec. 08, 2021]