Introduction: I didn’t pay much attention to the way Java creates objects at first, because I basically only knew how to use new😂, until 58 interviewer asked me which way Java can create objects. So I’ve cleaned up a little bit a couple of ways to create objects.

1. Use the new keyword to create an object

This is the most common and easy way to create objects in Java. This is done by calling the constructor (with or without parameters…). Object that creates the object. String name = new String(“hello”); What does the JVM do when it executes this statement?

  1. First check the constant pool of the method area to see if there is a symbolic reference to the parameter after new (that is, the class name), and to see if there is any loading information for the class (that is, if it has been loaded parsed and initialized). If it has already been loaded, it will not be loaded, otherwise it will perform the whole loading process of the class.
  2. Once the class is loaded, three things are done:

    A. Allocate memory to the instance: this memory stores the object’s own instance variables and instance variables inherited from the parent class (even if the instance variables inherited from the superclass may be hidden or allocated space), and these instance variables are given default values (zero); B. Call constructor to initialize member field: In the process of Java object initialization, there are three main structures to perform object initialization, namely instance variable initialization, instance code block initialization and constructor initialization; The c, user objects refer to the allocated memory space: note that the new operation is not an atomic operation, and the order of b and C may be reversed.

  • For details on how to load and instantiate classes in Java, see his blog: Class initialization and instantiation, load timing, and load process

2. Use the Clone method to create an object

Clone means to make a clone. When the Clone () method is used on an object (provided that the clone method is already implemented on the corresponding class), the JVM allocates memory for the copied object, creates new objects, and copies all the values of the copied object. The clone() method belongs to the Object class. Clone is copied in the heap memory in binary mode and reallocated a chunk of memory to the Object. The Clone method of the Object class is a native method, and its annotation reads: Creates and returns a copy of this object. The precise meaning of “copy” may depend on the class of the object. The general intent is that, for any object {@code x}, the expression:

  1. For an object to support Clone, the corresponding class must implement the Cloneable interface and override the Clone method in this class. In fact, the Cloneable interface is equivalent to a valid proof, indicating that this class can be clone legally; A class implements the Cloneable interfaceCloneable interface to indicate to the {@link java.lang.Object#clone()} method that it is legal for that method to make a field-for-field copy of instances of that class.
  2. The clone() method of the Object class is thread-safe;
  3. Clone () has two modes: shallow copy and deep copy.

    Shallow copy is to copy the value (surface layer) of the object to be copied. If the attribute of the object to be copied has reference type, only the referenced address is copied. The deep copy is to copy all the values of the object to be copied (deep copy). If the object to be copied has attributes of the reference type, the corresponding objects of the attributes of the reference type must also be copied. Deep copy and deep copy and not completely deep copy, in fact, deep copy is very difficult;

Using the clone object as a clone object, you can use the same object as a clone object.

public class Animal implements Cloneable{
    private String name = null;
    private int age = 0;

    public Animal(){ }

    public Animal(String name, int age){
        this.name = name;
        this.age = age;
    }

    public String getName() {return name;
    }

    public void setName(String name){
        this.name = name;
    }

    public int getAge() {return age;
    }

    public void setAge(int age){
        this.age = age;
    }

    @Override
    protected Object clone() throws CloneNotSupportedException {
        Animal animal = (Animal) super.clone();
        animal.name = new String(name);
        return animal;
    }

    public static void main(String[] args) throws CloneNotSupportedException {
        Animal dog = new Animal("Dog", 1);
        Animal smallDog = (Animal)dog.clone();
        System.out.println("dog:" + dog.getName() + "," + dog.getAge());
        System.out.println("smallDog:" + smallDog.getName() + ","+ smallDog.getAge()); System.out.println(dog); System.out.println(smallDog); }}Copy the code

The program results are as follows: Dog: dog, 1 smallDog: dog, 1 createobject.Animal@4554617c createobject.Animal@74a14482 So the Clone Dog object succeeds;

3. Use reflection to create objects

3.1Java Reflection mechanism

First, explain what Java’s reflection mechanism is; Java reflection allows you to know all the properties and methods of any class at runtime. For any object, you can call any of its methods and properties. This ability to dynamically retrieve information and invoke methods on objects is called Java’s reflection mechanism. An important part of the reflection mechanism is the “runtime”, which allows us to load, explore, and use.class files that are completely unknown at compile time while the program is running. In other words, a Java program can load a.class file whose name is not known until runtime, then learn of its complete construction and generate its object entities, or set values for its fields, or call its methods.

3.2 Using Reflection to create objects

There are two main steps:

  1. Get an instance of a Class object by:
    • Class. ForName (” Class full path “);
    • The name of the class. The class; Such as: Animal. The class;
    • The object name. GetClass ();
  2. Create instance objects of class objects by reflection; After obtaining an instance of a Class object, you can create an instance of a Class object through Java reflection. There are two main ways:
    • Class.newinstance () : To call a constructor without arguments, make sure there are no visible constructors in the Class. Otherwise, an exception will be thrown.
    • Call class object constructor:
  3. Cast to user required type;

Here’s a simple example:

public class Apple {
    private int price;
    protected String color;
    public String name;

    public Apple(){}

    public Apple(String name, int price, String color){
        this.name = name;
        this.price = price;
        this.color = color;
    }

    public int getPrice() {
        return price;
    }

    public void setPrice(int price){
        this.price = price;
    }

    public String getColor() {return color;
    }

    public void setColor(String color){
        this.color = color;
    }

    public String getName() {return name;
    }

    public void setName(String name){
        this.name = name;
    }

    public String printMsg() {return "name:" + name + ", price:" + price + ", color:"+ color; } public static void main(String[] args) throws ClassNotFoundException, NoSuchMethodException, IllegalAccessException, InvocationTargetException InstantiationException {/ / normal new object Apple apple1 = new Apple ("Apple1", 6666, "red");
        System.out.println("Apple1:" + apple1);
        System.out.println("Apple1: "+ apple1.printMsg()); Class CLS = class.forname ("reflect.Apple"); Constructor appleConstructor = cls.getconstructor (); // Constructor appleConstructor = cls.getconstructor (); / / according to the Object Constructor newInstance method for Object class Object reflection appleObject = appleConstructor. NewInstance (); // Cast Apple apple2 = (Apple)appleObject; System.out.println("Apple2:" + apple2);
//        System.out.println("Apple2:" + appleObject);
        System.out.println("Apple2: "+ apple2.printMsg()); }}Copy the code

Apple1:reflect.Apple@4554617c Apple1: name:Apple1, price:6666, color:red Apple2:reflect.Apple@74a14482 Apple2: Name :null, price:0, color:null Apple1 and Apple2 store the address is not the same, the reflection of an Apple object, using the constructor without arguments, so apple2 reference to the object attribute value is the default value. About the detailed content of reflection in the follow-up to write a separate article;

4. Create objects using deserialization

  1. Serialization:

    Speaking of deserialization, serialization is first introduced; What is serialization? The process of changing a variable from memory into something that can be stored or transferred is called serialization (explained on Liao xuefen’s official website), which is actually writing an object into an IO stream. Classes to be serialized in Java must implement the Serializable interface;

  2. Serialization scenario:

    • All objects that can be transported over the network must be serializable; In the case of RMI (Remote Method Invoke), arguments passed in or objects returned are serializable, otherwise an error occurs;
    • All Java objects that need to be saved to disk must be serializable; It is generally recommended that every JavaBean class created by a program implement a Serializeable interface;
  3. Serialization and deserialization implementation: The class corresponding to the serialized object must implement the Serializable interface or Externalizable interface;

    • Example of Serializable interface Serializable: The Serializable interface is a markup interface that does not implement any methods. Once this interface is implemented, the objects of this class are serializable; Of course, there is also the Externalizable interface serialization method, the details will be introduced separately;
    • Deserialization: recovering objects from AN IO stream;
import java.io.Serializable; /** * public class Person implements Serializable {private String name; private int age; Public Person(String name, int age){// system.out.println ("Deserialization, did you call me?");
        this.name = name;
        this.age = age;
    }

    @Override
    public String toString() {return "Person{ " + "name = '" + name + '\'' + ", age = " + age + '}'; }}Copy the code
import java.io.FileOutputStream; import java.io.ObjectOutputStream; /** * serialization steps: */ public class writeObject {public static. */ public class writeObject {public static Void main(String[] args){try{// create ObjectOutputStream ObjectOutputStream = new ObjectOutputStream(new FileOutputStream("person.txt")); S Person Person = new Person("Fung Shuying", 25);
            objectOutputStream.writeObject(person);
        }catch (Exception e){
            e.printStackTrace();
        }

        System.out.println("success~"); }}Copy the code
import java.io.FileInputStream; import java.io.ObjectInputStream; /** * Deserialization steps: * â‘  Create an ObjectInputStream input stream * â‘¡ call ObjectInputStreamreadPublic class ReadObject {public static void main(String[] args){try{// Create an ObjectInputStream ObjectInputStream objectInputStream = new ObjectInputStream(new FileInputStream("person.txt")); Person person = (Person)objectInputStream.readObject(); System.out.println(person); }catch (Exception e){ e.printStackTrace(); }}}Copy the code

When deserializing, you can add output statements to the constructor of the corresponding class to test whether the constructor is called when deserializing. The results show that deserialization does not invoke the constructor; Antisequence objects are objects generated by the JVM itself, not by constructors;