# Generics in Java Example

In 
Published 2023-06-12

# Theory

This tutorial explains what is and how to use Generics in Java.

Java Generics was introduced to deal with type-safe objects.

Java Generics allows us to create a single class, interface, and method that can be used with different types of data (objects).

Please take a look at the following example and read carefully the comments. The code is self-explanatory.

# Example

From the base application downloaded from Spring Initializr, I updated the main class and added some classes as below:

MyClass1.java
package com.example.demo;

public class MyClass1 {

    String str1;

    public String getStr1() {
        return str1;
    }

    public void setStr1(String str1) {
        this.str1 = str1;
    }

    public MyClass1 (String str1) {
        this.str1 = str1;
    }

    public int returnValue() {
        return str1.length();
    }
}
MyClass2.java
package com.example.demo;

public class MyClass2 {

    int value1;

    public int getValue1() {
        return this.value1;
    }

    public void setValue1(int value1) {
        this.value1 = value1;
    }

    public MyClass2(int value1) {
        this.value1 = value1;
    }

    public int returnValue() {
        return value1;
    }
}
MyGenericClass.java
package com.example.demo;

// Generic Class : when instantiated, we use a generic class for the constructor
public class MyGenericClass <T> {

    T myClass;

    public MyGenericClass(T myClass1) {
        this.myClass = myClass1;
    }

    public String objAddress() {
        var valToReturn = this.myClass.toString();
        return valToReturn;
    }

    // Generic methods : input/output variable types could be generic
    public <U> void getVariableType(U var1) {
        System.out.println( "We deal with a variable of "+var1.getClass().getName()+" type.");
    }
}
DemoApplication.java
package com.example.demo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ApplicationContext;
import java.util.concurrent.ExecutionException;

@SpringBootApplication
public class DemoApplication {

	public static void main(String[] args) throws InterruptedException, ExecutionException {

		// Create the application context and start Spring Boot
		ApplicationContext appContext = SpringApplication.run(DemoApplication.class, args);

		System.out.println("DemoApplication - start");

		MyClass1 myClass1 = new MyClass1("Hello");
		MyClass2 myClass2 = new MyClass2(90);

		MyGenericClass<MyClass1> intObj1 = new MyGenericClass(myClass1);
		MyGenericClass<MyClass2> intObj2 = new MyGenericClass(myClass2);

		System.out.println("Address for MyClass1 = "+intObj1.objAddress());
		System.out.println("Address for MyClass2 = "+intObj2.objAddress());

		intObj1.getVariableType(myClass2);

		System.out.println("DemoApplication - end");
	}
}

When the code run, we have the following output in the console:

DemoApplication - start
Address for MyClass1 = com.example.demo.MyClass1@73511076
Address for MyClass2 = com.example.demo.MyClass2@7927bd9f
We deal with a variable of com.example.demo.MyClass2 type.
DemoApplication - end

Process finished with exit code 0

# Bounds on Generics Classes

  • we can limit the object types a generic class could work with

For doing this we can use the keyword "extends":

public class MyGenericClass <T extends Number> {
    
}

# Bounds on Generics Methods

  • we can limit the object types a generic method could work with as well. The generic types could be used as parameters or as response type.

For doing this we can use the keyword "extends":

public class MyGenericClass <T extends Number> {

    public <U extend Number> void getVariableType(U var1) {
        // Do something
    }    
}
  • If the input or output object type are generics defined before we can also restrict the generic type we are using with the method.
public class MyGenericClass <T extends Number> {

    public void getVariableType(MyGenericObject<? extends ClassA>) {
        // Do something
    }    
}