Which Java Types Can Implement Interfaces?
Last Updated :
31 Oct, 2022
In Java there is no concept of multiple-inheritance, but with the help of interface we can achieve multiple-inheritance. An interface is a named collection of definition. (without implementation)
An interface in Java is a special kind of class. Like classes, interface contains methods and members; unlike classes, in interface all members are final and all methods are abstract.
//interface definition
//we use interface keyword to declare interface
interface <interface_name>{
variable declaration; //
method declaration; //does not implement them, are always public and abstract.
}
//class which implements interface
public class <class_name> implements <interface_name>{
//the methods declared my interface class should be implemented by the class which implement it.
}
- We cannot instantiate an interface in java that means we cannot create an object of the interface class.
- A class implementing an interface must provide an implementation for all it’s methods unless it’s an abstract class.
- By default, any attribute of the interface is public, static, and final. So, there is no need to provide access modifier to the attribute but if it complies does not complain about it either.
- By default methods are implicitly abstract and public, it makes total sense because the methods don’t have a body and so subclasses can provide the method implementation.
- Static methods cannot be declared in the interfaces – these methods are never abstract and do not express the behavior of the object
Java Types Implementing Interface
There are primarily 5 java types that can implement interfaces that are listed below which we are going to explore over later to depth as follows:
- Java Class
- Java Abstract Class
- Java Nested Class
- Java Enum
- Java Dynamic Proxy
Type 1: Java Class
When a class implements an interface, it is essentially signing a contract. Either the class must implement all the methods declared in the interface and its super interfaces, or the class must be declared abstract.
To declare a class that implements an interface, include an implements keyword in the class declaration. Your class can implement more than one interface, so the implements keyword is followed by a comma-separated list of the interfaces implemented by the class.
Example
Java
import java.io.*;
interface Animal {
int x = 4 ;
void sound();
}
class Chicks implements Animal {
public void sound() { System.out.println( "cheep" ); }
public static void main(String[] args)
{
Chicks c = new Chicks();
c.sound();
System.out.println( "The value of x = " + x);
}
}
|
Output
cheep
The value of x = 4
Type 2: Java Abstract Class
Interface and abstract classes are similar in many ways, but an abstract class allows single inheritance whereas interface allows multiple inheritances. If a class includes an interface but does not fully implement the methods required by the interface, then the class must be declared an abstract class.
When we implement an interface to an abstract class, its means that the abstract class inherited all the methods of the interface. It is not necessary to implement all the methods in an abstract class, however, it comes to abstract class (by inheritance too), so the abstract class can leave some of the methods in the interface without implementation here. But, when this abstract class will be inherited by some class, they must have to implement all those unimplemented methods there in the abstract class.
Example
Java
import java.io.*;
interface Animal {
public void sound();
public void breed();
}
abstract class Cat implements Animal {
public void sound() { System.out.println( "meow" ); }
}
public class Cat1 extends Cat {
public void breed() { System.out.println( "Ragdoll" ); }
}
class Main {
public static void main(String[] args)
{
Cat1 c = new Cat1();
c.breed();
c.sound();
}
}
|
Type 3: Java Nested Class
Java has the ability to nest a class inside an interface. The nested class is implicitly public and static. Nesting class inside interface can be useful, especially when there is a relationship between the enclosing interface and the enclosed class. Nesting class inside interface can improve the source code’s readability. The class and interface with the same name, nesting can also help you avoid a name conflict between the two.
Example
Java
import java.io.*;
interface Animal {
public class Type {
public static void animal()
{
System.out.println( "The animal is cat" );
}
}
public void breed();
public void sound();
}
public class Cat implements Animal {
public void breed() { System.out.println( "Munchkin" ); }
public void sound() { System.out.println( "Meow" ); }
}
class MainClass {
public static void main(String args[])
{
Cat c = new Cat();
Animal.Type.animal();
c.breed();
c.sound();
}
}
|
Output
The animal is cat
Munchkin
Meow
Type 4: Java Enum
Enum can implement any interface in Java. Since enum is a type, similar to any other class and interface, it can implement any interface in java. This gives a lot of flexibility in some cases to use Enum to implement some other behavior.
Example
Java
import java.io.*;
interface Cat {
public void breed();
}
enum Breed implements Cat {
Siamese,
Persian,
Bengal,
Burmese;
public void breed()
{
System.out.print( "The breed is " + this );
}
}
public class MainClass {
public static void main(String args[])
{
Breed.Persian.breed();
}
}
|
Output
The breed is Persian
Type 5: Java Dynamic Proxy
A proxy calls the object method indirectly through the proxy object. java.lang.reflect API provides a class as Proxy and an interface as InvocationHandler. Together these two API creates a dynamic proxy class. Proxy class creates the dynamic proxy class on the basis of given parameters. InvocationHandler invokes the methods of dynamic proxy class.
Example
Java
package javaInterface;
import java.io.*;
interface Animal {
public void breed();
public void sound();
}
class Cat implements Animal {
public void breed() { System.out.println( "Ragdoll" ); }
public void sound() { System.out.println( "meow" ); }
}
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
class LoggingHandler implements InvocationHandler {
private final Object target;
private Map<String, Integer> calls = new HashMap<>();
public LoggingHandler(Object target)
{
this .target = target;
}
public Object invoke(Object proxy, Method method,
Object[] args) throws Throwable
{
String name = method.getName();
if (name.contains( "toString" )) {
return calls.toString();
}
calls.merge(name, 1 , Integer::sum);
return method.invoke(target, args);
}
}
import java.lang.reflect.Proxy;
import java.util.HashMap;
import java.util.Map;
class MainClass {
@SuppressWarnings ( "unchecked" )
public static <T> T withLogging(T target, Class<T> itf)
{
return (T)Proxy.newProxyInstance(
itf.getClassLoader(), new Class<?>[] { itf },
new LoggingHandler(target));
}
public static void main(String args[])
{
Cat c = new Cat();
Animal logged = withLogging(c, Animal. class );
logged.breed();
logged.sound();
System.out.println(logged);
}
}
|
Output:
Ragdoll
meow
{sound=1, breed=1}
Like Article
Suggest improvement
Share your thoughts in the comments
Please Login to comment...