Summary analysis based on generics in Java

  • 2020-04-01 01:46:45
  • OfStack

I can't tell you what generics are, but let's start with a question:

Defines a coordinate point class that can hold various types of data, such as integer, floating point, and string types

Since the variable type is initially uncertain, it is easy to imagine replacing it with the parent of all types, the Object class

No more nonsense, in code

Example 1: use Object to implement uncertain data type input


//This is the defined coordinate point class
class Point {
    private Object x;
    private Object y;

    //Object is used to represent an uncertain type
    public Point(Object x, Object y) {
        this.setX(x);
        this.setY(y);
    }
    public void setX(Object x) {
        this.x = x;
    }
    public Object getX() {
        return x;
    }
    public void setY(Object y) {
        this.y = y;
    }
    public Object getY() {
        return y;
    }

}

//The test class
public class Demo {
    public static void main(String[] args) {
        System.out.println(" Coordinates are expressed as floating point Numbers : ");
        Point p = new Point(12.23,23.21);
        //Here, the Object class is converted to the Double class, and then it is unboxed automatically, the same as the next two
        System.out.println("X The coordinates of the  " + (Double)p.getX());
        System.out.println("Y The coordinates of the  " + (Double)p.getY());
        System.out.println();

        System.out.println(" Coordinates are expressed as integers : ");
        Point p2 = new Point(12, 23);
        System.out.println("X The coordinates of the  " + (Integer)p2.getX());
        System.out.println("Y The coordinates of the  " + (Integer)p2.getY());
        System.out.println();

        System.out.println(" Coordinates are represented as strings : ");
        Point p3 = new Point(" North latitude 29 The degree of ", " East longitude 113 The degree of ");
        System.out.println("X The coordinates of the  " + (String)p3.getX());
        System.out.println("Y The coordinates of the  " + (String)p3.getY());
    }
}

So you can plug in different types of data, but remember, the data is still Object, which is the parent of all types

You have to be clear about what type you're passing in and then turn it down before you can use it

< img Alt = "" border = 0 SRC =" / / files.jb51.net/file_images/article/201305/2013050319061393.png ">

This satisfies the need, but it implies an element of insecurity. Why is it implied?

For example, we use new Point(12.23," 29 degrees north latitude ") to construct a Point object

And then I'm going to use (Double) to turn it down, and what happens?

Yes, the compilation will pass, but the cast exception will occur once run

< img Alt = "" border = 0 SRC =" / / files.jb51.net/file_images/article/201305/2013050319061394.png ">

It is also easy to avoid class conversion exceptions by replacing the Object declaration with a fixed type declaration (such as String x, String y), which causes errors to be reported at compile time

Then you can look for errors and fix them

But then we won't be able to meet the demand

To eliminate security concerns and plug in various data types, these folks introduced generics in JDK1.5

Let's see how to rewrite the above code with generics

Example 2: generic class


class Point<T> {
    //I'm going to use T for the type of uncertainty
    private T x;
    private T y;
    public Point(T x, T y) {
        this.setX(x);
        this.setY(y);
    }
    public T getX() {
        return x;
    }
    public void setX(T x) {
        this.x = x;
    }
    public T getY() {
        return y;
    }
    public void setY(T y) {
        this.y = y;
    }
}

public class Demo {
    public static void main(String[] args) {
        System.out.println(" Coordinates are expressed as floating point Numbers : ");
        //After rewriting with generics, there is no need to do downward transformation processing with the data
        Point<Double> p = new Point<Double>(12.23,23.21);
        System.out.println("X The coordinates of the  " + p.getX());
        System.out.println("Y The coordinates of the  " + p.getY());
        System.out.println();

        System.out.println(" Coordinates are expressed as integers : ");
        Point<Integer> p2 = new Point<Integer>(12, 23);
        System.out.println("X The coordinates of the  " + p2.getX());
        System.out.println("Y The coordinates of the  " + p2.getY());
        System.out.println();

        System.out.println(" Coordinates are represented as strings : ");
        Point<String> p3 = new Point<String>(" North latitude 29 The degree of ", " East longitude 113 The degree of ");
        System.out.println("X The coordinates of the  " + p3.getX());
        System.out.println("Y The coordinates of the  " + p3.getY());
    }
}

After using generics, you can reduce the existence of security concerns

< img Alt = "" border = 0 SRC =" / / files.jb51.net/file_images/article/201305/2013050319061395.png ">

If we deliberately pass in different data types at this time:

Point< Double> P = new Point< Double> (" 29 degrees north latitude ",12.22);

Then, an error will be reported at compile time

< img Alt = "" border = 0 SRC =" / / files.jb51.net/file_images/article/201305/2013050319061396.png ">

Generics are defined, but if you don't use the generics mechanism in the constructor, it treats the data as an Object

The main purpose of this is to be compatible with older code prior to JDK1.4, such as

Point p = new Point(22.11,23.21);

The end result is the same, but it prompts a warning at compile time

< img Alt = "" border = 0 SRC =" / / files.jb51.net/file_images/article/201305/2013050319061397.png ">

 

Example 3: generic methods

As you can see from the above example, once the object type is specified in the constructor, the same type is used throughout the class

The most typical example is in the collection framework, such as ArrayList< Integer> Al = new ArrayList< Integer> (a);

At this point, all object types that operate in al are integers

However, there are times when we don't want to be able to fix the object we're working on, but rather to be able to use generic techniques more flexibly

This is the time to try a generic approach


//Generics are no longer defined after the class name
class Print {
    //Define generics in methods
    public <T> void print(T t) {
        System.out.println(t);
    }

    public <E> void show(E e) {
        System.out.println(e);
    }
}

public class Demo {
    public static void main(String[] args) {
        Print p = new Print();
        p.print(12);
        p.print("hello");
        p.show(new Integer(33));
        p.show(23);
    }
}

So it's no different from using an Object in a method, right

In addition, JDK1.5 after the addition of automatic packaging function, eliminating the need for downward transformation trouble

< img Alt = "" border = 0 SRC =" / / files.jb51.net/file_images/article/201305/2013050319061398.png ">

 

Example 4: generic interface


//Define a generic interface
interface Inter<T>
{
    public void print(T t);
}

//Implementation method 1:
class InterDemo1 implements Inter<String> {
    public void print(String t) {
        System.out.println("print: " + t);
    }
}

//Implementation method 2:
class InterDemo2<T> implements Inter<T> {
    public void print(T t) {
        System.out.println("print: " + t);
    }
}

class Demo {
    public static void main(String[] args) {
        InterDemo1 id1 = new InterDemo1();
        id1.print("hello");
        InterDemo2<Integer> id2 = new InterDemo2<Integer>();
        id2.print(new Integer(23));
    }
}

There are two ways to implement a generic interface. One is to specify the generic type at implementation time

The other is to still use generics and determine the generic type at construction time

< img Alt = "" border = 0 SRC =" / / files.jb51.net/file_images/article/201305/2013050319061399.png ">


Related articles: