Private methods in interfaces are methods with a body that only the other methods of the same interface can call. Implementing classes and callers cannot see such a method, so it stays an internal helper of the interface.
We use private interface methods to share code between default methods or static methods, without adding that shared code to the public API of the interface. Before Java 9, the shared code had to go into another default method, which every implementing class inherited and could call.
The following example has two default methods that build a greeting with one private helper.
interface Greeter {
default String morning(String name) {
return greet("Good morning", name);
}
default String evening(String name) {
return greet("Good evening", name);
}
private String greet(String prefix, String name) {
return prefix + ", " + name.strip() + "!";
}
}
Greeter greeter = new Greeter() {};
String morning = greeter.morning(" Ana "); // "Good morning, Ana!"
String evening = greeter.evening("Ben"); // "Good evening, Ben!"
Notice that greet() is not part of what Greeter offers to callers, so greeter.greet(…) does not compile. We look at what an interface can contain today, private instance and private static methods, the rules the compiler enforces, a comparison with default and static methods, and a real-world example.
1. What a Java Interface Can Contain
An interface started as a list of abstract methods and constants. Java 8 added default and static methods with a body, and Java 9 added private methods so that these bodies can share code. Every member type is still valid in Java 25.
| Member | Modifiers | Has a body | Visible to implementing classes | Since |
|---|---|---|---|---|
| Abstract method | public abstract (implicit) | No | Yes, must be implemented | Java 1.0 |
| Constant | public static final (implicit) | n/a | Yes | Java 1.0 |
| Default method | public default | Yes | Yes, inherited | Java 8 |
| Static method | public static | Yes | Called as Interface.method() | Java 8 |
| Private method | private | Yes | No | Java 9 |
| Private static method | private static | Yes | No | Java 9 |
Fields in an interface are always public static final, so an interface cannot have private fields. Private methods add behavior, not state, which keeps interfaces different from abstract classes.
2. Private Instance Methods
A private instance method is declared with private and a body. Default methods and other private instance methods of the same interface can call it, and inside it, this refers to the object that implements the interface, so it can also call the abstract methods.
The following calculator interface adds the even numbers or the odd numbers of its arguments. Both default methods delegate to one private method add() that takes the condition as an IntPredicate.
interface CustomCalculator {
default int addEvenNumbers(int... nums) {
return add(n -> n % 2 == 0, nums);
}
default int addOddNumbers(int... nums) {
return add(n -> n % 2 != 0, nums);
}
private int add(IntPredicate predicate, int... nums) {
return IntStream.of(nums).filter(predicate).sum();
}
}
CustomCalculator calc = new CustomCalculator() {};
int evens = calc.addEvenNumbers(1, 2, 3, 4, 5, 6, 7, 8, 9); // 20
int odds = calc.addOddNumbers(1, 2, 3, 4, 5, 6, 7, 8, 9); // 25
Without the private method, the stream code would be repeated in both default methods. Making add() a third default method would also remove the repetition, but every implementing class would inherit it and every caller could use it.
3. Private Static Methods
A private static method belongs to the interface itself and has no this. Static methods of the interface can call it, and so can default and private instance methods. It fits helpers that work only on their arguments, such as validation or formatting.
interface Temperature {
static double toFahrenheit(double celsius) {
return round(celsius * 9 / 5 + 32);
}
static double toCelsius(double fahrenheit) {
return round((fahrenheit - 32) * 5 / 9);
}
private static double round(double value) {
return Math.round(value * 10) / 10.0;
}
}
double warm = Temperature.toFahrenheit(21.5); // 70.7
double cold = Temperature.toCelsius(40); // 4.4
The reverse call does not work. A static method cannot call a private instance method, because there is no object to call it on, and the compiler reports “non-static method cannot be referenced from a static context”.
4. Rules for Private Methods in Interfaces
A private interface method must have a body, and it cannot be combined with abstract or default. The compiler checks every rule, and the table lists the javac error for each broken rule on JDK 25.

| Rule | Code that breaks it | javac error |
|---|---|---|
| Must have a body | private void log(); | missing method body, or declare abstract |
| Cannot be abstract | private abstract void log(); | illegal combination of modifiers: abstract and private |
| Cannot be default | private default void log() {} | illegal combination of modifiers: private and default |
| Static code cannot call private instance methods | static void s() { helper(); } | non-static method helper() cannot be referenced from a static context |
| Not inherited by implementing classes | helper() called in an implementing class | cannot find symbol |
| Only public or private methods | protected void log(); | modifier protected not allowed here |
Because a private method is not inherited, an implementing class can declare a method with the same name and parameters. It is a separate method and does not override the private one, so the default methods of the interface keep calling their own helper.
// does not compile: cannot find symbol, greet() is private to Greeter
class LoudGreeter implements Greeter {
String shout(String name) {
return greet("HEY", name).toUpperCase();
}
}
5. Private vs Default vs Static Interface Methods
The three method kinds with a body differ in who can call them and whether a class can override them. Choosing the wrong one either exposes a helper or blocks a class from customizing behavior.
| Question | default | static | private / private static |
|---|---|---|---|
| Callers can use it | Yes, on an instance | Yes, as Interface.method() | No |
| Implementing class inherits it | Yes | No | No |
| Implementing class can override it | Yes | No | No |
| Typical use | Optional behavior with a sensible default | Factory or utility methods | Shared code of the other methods |
A simple rule follows from the table. If an implementing class should be able to change the behavior, we use a default method. If the code is only a building block for other methods of the interface, we make it private.
6. Sharing Message Formatting in a Notifier Interface
Say an online shop sends order updates by email and by SMS. Both channels implement one interface, which has default methods for the standard messages. Each message needs the same order number formatting and the same check of the customer name, and that shared code must not become part of the public interface.
interface OrderNotifier {
String send(String customer, String text);
default String shipped(String customer, int orderNo) {
return send(checked(customer), "Order " + format(orderNo) + " has shipped");
}
default String delivered(String customer, int orderNo) {
return send(checked(customer), "Order " + format(orderNo) + " was delivered");
}
private String checked(String customer) {
if (customer == null || customer.isBlank()) {
throw new IllegalArgumentException("customer is required");
}
return customer.strip();
}
private static String format(int orderNo) {
return "#" + String.format("%06d", orderNo);
}
}
class SmsNotifier implements OrderNotifier {
public String send(String customer, String text) {
return "SMS to " + customer + ": " + text;
}
}
OrderNotifier sms = new SmsNotifier();
String shipped = sms.shipped("Ana", 4217); // "SMS to Ana: Order #004217 has shipped"
String missing = sms.delivered(" ", 4217); // IllegalArgumentException: customer is required
The SmsNotifier class implements only send(). It inherits both message methods and cannot call or change checked() or format(), so every channel validates and formats the same way. An email channel would be one more small class with its own send().
7. How Interfaces Changed Since Java 1.0
Private interface methods were planned for Java 8 together with default methods but were dropped late in that release. They arrived in Java 9 with JEP 213, and the Java features list shows the other changes of each release.
| Java version | Interface change |
|---|---|
| Java 1.0 | Abstract methods and constants |
| Java 8 | Default methods and static methods |
| Java 9 | Private methods and private static methods (JEP 213) |
| Java 17 | Sealed interfaces with permits (JEP 409) |
8. Private Interface Methods FAQs
Most questions about private interface methods compare them with default methods and abstract classes.
8.1. Can an Interface Have Private Methods in Java?
Yes, since Java 9. An interface can declare private instance methods and private static methods, and both must have a body.
8.2. Can a Private Interface Method Be Overridden?
No. Private methods are not inherited, so there is nothing to override. A class can declare a method with the same signature, but the interface code keeps calling its own private method.
8.3. Can a Default Method Call a Private Static Method?
Yes. Default methods and private instance methods can call both private instance and private static methods. Only static methods are limited to private static methods.
8.4. Why Not Use an Abstract Class Instead?
An abstract class can hold private methods and fields, but a class can extend only one class. An interface with private methods keeps the multiple inheritance of types and still hides its helper code.
9. Conclusion
Private interface methods let default and static methods share code without exposing it. A private instance method can use this and the abstract methods, and a private static method works only on its arguments, so static methods can call only the static kind.
The compiler enforces the rest. Private methods need a body, cannot be abstract or default, and are not inherited. They keep an interface small for callers, which is the same goal encapsulation has for classes, and the OOP basics apply to interfaces the same way.
10. References
- JEP 213, Milling Project Coin
- JLS 25, Interface Method Declarations
- Oracle Java Tutorial, Default Methods
Happy Learning !!
hello, everyone I have a doubt in java 9 features in interface is that if private static method can also used in default method then what is the purpose of private instance method
Nice info with examples
A Java interface is used to specify what is to be done but not how it is to be done. Inheritance is generally in the context of interfaces when extending an interface is necessary.
Point no 4 which says non static method can not be used inside static method. This is logically obvious also as at that time non static methods are not available in memory. Please highlight this logic and put it as a general rule.