JAVA / METHODS
Defining and calling static methods
Define static methods next to main, call them inside their own class or as ClassName.method(...), and fix the 'non-static context' error on sight.
What you will learn
- Declare helpers static so main can call them without creating an object
- Call same-class statics by bare name; other classes' as ClassName.method(arg)
- Read 'non-static method ... from a static context' as: that method wants an object
- Method order inside a class never affects whether a call resolves
Understanding Defining and calling static methods
A static method is a named piece of code that belongs to the class it is written in rather than to any object built from that class. You declare it inside the class braces, at the same level as main: any modifiers, then static, then the return type, the name, and the parameter list. Because it hangs off the class itself, the JVM can invoke it as soon as the class is loaded, which is exactly why main is static: at startup there is no object for it to belong to.
Inside the same class you call a static method by writing its name and arguments, with no prefix and no object anywhere in sight. Position in the file is irrelevant, because javac collects every member declaration of the class before it type-checks any method body, so a call in main can reach a method written fifty lines lower. From outside the class you name the owner first, as in Math.round(x) or Integer.parseInt(s); the class name is the address that tells the compiler where to look.
The restriction that trips people up follows directly from that ownership: a static method has no this, so the only things it can reach are its parameters, its own locals, and other static members of the class. That is why javac reports "non-static method ... cannot be referenced from a static context" when main calls a helper that is missing static, the helper is asking for an object main does not have. Read static as "one per class", not as "constant" or "remembers values between calls".
public class Temperature {
static double toFahrenheit(double celsius) {
return celsius * 9 / 5 + 32;
}
public static void main(String[] args) {
double c = 21.5;
System.out.println(c + "C is " + toFahrenheit(c) + "F");
System.out.println("Midpoint: " + average(10.0, 25.0));
System.out.println("Rounded: " + Math.round(toFahrenheit(c)));
}
// written after main on purpose: declaration order does not matter
static double average(double a, double b) {
return (a + b) / 2;
}
}A static method belongs to the class itself, so it can be called through the class name with no object in existence.
Worked examples
Calling a static method that lives in another class
Shows that a static method in a different class is reached through its class name, with no object created.
class Digits {
static int sumOfDigits(int n) {
int total = 0;
while (n > 0) {
total += n % 10;
n /= 10;
}
return total;
}
}
public class Main {
public static void main(String[] args) {
System.out.println(Digits.sumOfDigits(4091));
System.out.println(Digits.sumOfDigits(7));
}
}Example explained
Line 1Digits.sumOfDigits(4091) names the class first because the method is not a member of Main; the bare name sumOfDigits(4091) would fail with "cannot find symbol".
Line 2No new Digits() appears anywhere, the method is callable the moment the Digits class is loaded.
Line 3The loop peels digits with % 10 and /= 10 until n hits 0, so the first call returns 4 + 0 + 9 + 1.
Line 4The second call runs one iteration and returns 7, proving the method keeps no state between calls.
A static method touching a static field
Demonstrates that the only fields a static method can use directly are the class's own static ones, shared by every call.
public class Counter {
static int calls = 0;
static void hit(String label) {
calls++;
System.out.println(label + " -> calls=" + calls);
}
public static void main(String[] args) {
hit("first");
hit("second");
hit("third");
System.out.println("total " + Counter.calls);
}
}Example explained
Line 1hit("first") needs no prefix because the call site and the method are members of the same class.
Line 2calls is static, so there is exactly one copy owned by the class and all three calls update it.
Line 3If calls were declared without static, the line calls++ inside hit would not compile, since hit has no object to read the field from.
Line 4The last line writes Counter.calls, the qualified form of the same field; inside the class both spellings mean the same variable.
Important notes
static is about ownership, not immutability or memory: local variables in a static method are created fresh on every call, unlike C's static locals.
A static method can also be called through a reference, obj.method(), and it even runs when the reference is null because the target is picked from the compile-time type; call it through the class name instead.
Common mistakes
Leaving static off a helper that main calls: compilation stops with "non-static method helper() cannot be referenced from a static context", and no class file is produced.
Writing the helper inside main's braces: Java has no methods inside methods, so javac rejects the header as an illegal start of expression.
Calling another class's static method without the class name: you get "cannot find symbol: method" at the call site even though the method itself compiles fine where it is defined.
Try it yourself
Change, predict, then run
In a class Clock with a main method, write static String pad(int n) that returns "07" for 7 and "12" for 12, and print pad(5) + ":" + pad(30). Then move pad into a second class named Format and fix the call site so the program still compiles.
Open the Java workspaceCheck your understanding
A file has static void main(String[] args) plus a method int total(int[] a) declared without static. main calls total(nums) and javac reports "non-static method total(int[]) cannot be referenced from a static context". What is the compiler actually objecting to?
- total is declared as something you call on an object, and main is running without one
- total must appear above main in the file so the compiler can see it before the call
- total returns int while main returns void, so their types are incompatible
- total must be public before another method in the same class is allowed to call it
Show answer
Omitting static makes total a member of each object of the class, so a call needs a receiver; main belongs to the class and has no this to supply, hence the error. Declaration order is a red herring: javac reads every member of a class before checking any body, so calling a method written below main is perfectly legal.