Warm prompt

Hello everyone, I am Cbiltps. In my blog, if there is a sentence that is difficult to understand, or a key point that is difficult to express in words, I will have pictures. So it is very important to illustrate my blog!!

And a lot of knowledge in the code comments, so code comments are also very important!!

This article before and after the logical order is very important, be sure to look back, slowly look!!

This article was adapted from CSDN!

Please be patient to finish reading.

Later I will write a blog about classes and objects, in fact, before learning this blog must have a certain understanding of classes and objects! If you read the class and object blog, and then read this object oriented article, you’ll have a step by step understanding!

Then, at the end of this article, I will unfold a simple and comprehensive object-oriented training (link directly at the end), you will see! After learning, you will have a preliminary understanding of object oriented!

Another point: this article is more horizontal expansion, the whole process of more than 30,000 words! We will see a wealth of knowledge points in learning, coverage is more complete!

So, the point of this blog post today ismillet,alibaba,baidu,VIVO,tencent,ctrip,shell,Meituan,headlines,netease,jingdong,dropsCompanies such asoften!!!!!!!!!

This chapter focuses on

  • package
  • inheritance
  • polymorphism
  • An abstract class
  • interface

The text start


1. The package


A package is a way of organizing a class. The main purpose of using a package is to ensure that the class is unique.

The above words are difficult to understand, let’s not dwell on this for a moment, directly use an example (see below)!

1.1 Importing classes in the package

For example, when printing an array, we import the class in the package:

package com.company;

import java.util.Arrays;// Calls the Arrays class from util

public class Main {

    public static void main(String[] args) {
	    int[] array = {1.2.3.4.5};
        System.out.println(Arrays.toString(array));// Print an array as a string}}Copy the code

Notice one problem: toStringThis method is made up ofClass name (Arrays)Call, so this method is oneA static method(Press CTRL and mouse to enterAnd into theArrays.javaFile, as shown below)! So any method called directly by the class name must be static, we do not care how this method is executed, this is officially written, directly call can!

So, which bag is it under?

Open the file on it (Arrars.java), as shown belowWe can find this file (Arrars.java) path:About the aboveThe package keywordWhat is it? I’ll tell you later! And look at the next little bit (Arrars. In Java), andThe import keyword! Then ask:importandpackageWhat’s the difference?

  • packageIt’s generated after you run the program.class filesPut it all in the package you define for later call management.
  • An import is a class in a package that needs to be called when a program is written.

That is to say, if we need to use some Java class library code, we need to import!

Here’s another import example:

// Import mode 1
package com.company;

import java.util.Date;// Import it here

public class Main {

    public static void main(String[] args) {
        Date date = newDate(); }}Copy the code
// Import mode 2
package com.company;

public class Main {

    public static void main(String[] args) {
        java.util.Date date = new java.util.Date();// This import can also be done, but more troublesome, recommended method 1}}Copy the code

Remember: Only one can be importedConcrete classesCannot import oneThe specific package!

And then the next question: We see someone importing packages like this, here*What does that mean?

import java.util.*;
Copy the code
  • * is a wildcard character: it means to import all classes under this package!

Question:utilThere are a lot of classes below, did all of a sudden import?

No, when Java processes, it takes whoever it needs!

In C language, after importing through the include keyword, the contents of the head file will be taken over!

But this way (import java.util.*;) The scope of the import is too wide, you may not grasp, yesThere will be conflicts(following), you are advised to importThe concrete class name!But suppose you wanted toIf you use the Date at the bottom of the other package, you can’t identify it(See below) : The solution is:Import with the full class name!

// The code is organized like this:
package com.company;

import java.util.*;
import java.sql.*;
// Both packages have Date classes. To avoid conflicts, use the following operations

public class Main {

    public static void main(String[] args) {
        java.util.Date date = new java.util.Date();// Import with the full class name}}Copy the code

1.2 Static Import

Under normal circumstances, static import with very little, understand can!

package com.company;

import static java.lang.System.*;
import static java.lang.Math.*;

public class Main {

    public static void main(String[] args) {
        out.println("123");Static imports are easy to write
        out.println(max(12.23));// However, it is not recommended to write in this way}}Copy the code

1.3 Putting classes into packages

Without further ado, let’s go straight to the steps:

  1. Create a new package

2. Create a class

And at the same time you can seediskThe directory structure is already created automatically by IDEA

Ground rules (note the following) :

  • Add a package statement at the top of the file to specify which package the code is in
  • The package name must be lowercase
  • The package name needs to be as unique as possible, usuallyUse the inverted form of the company’s domain name(such as:com.xxxxx.www)
  • The package name matches the code path, such as createcom.cbiltpsPackage, then there will be a corresponding pathcom/cbiltpsTo store code
  • If a class does not have a package statement, the class is placed in a default package

After the above steps, return to the first sentence of section 1: PACKAGES are a way of organizing classes, and the main purpose of using packages is to ensure that classes are unique.

How do you guarantee the uniqueness of a class? In fact, the same directory on the disk (under the same package) can only have a file (class) with the same name, and the package name is not the same, the path is not the same, also do not interfere with each other!

1.4 Control of packet access permission

Package access: As the name implies, only available within the current package.

For example, when you do not add any access-modifier qualifiers to a member variable, it is package access.

Due to theDifferent packages are displayed, it is not convenient to show the code directly, so I show the screenshot.It follows that,Cbiltps packageIn theCan’taccessCompany packageIn theVal values, soPackage accessCan only be used in the current package!

1.5 Common System packages

  1. Java.lang: System common basic classes (String, Object).

This package is automatically imported from JDK1.1, no import required! 2. Java.lang.reflect: Java Reflection programming package 3. Java.net: Network programming development package. Java. SQL: support package for database development. 5. Java.util: A utility package provided by Java. IO: I/O programming development kit.


2. The inheritance


Before moving on to this section, let’s review the basic characteristics of object Orientation.

  • encapsulation: data members and methods that are not necessarily exposed, usedprivateKeyword modification (forSecurity!)
  • inheritance: To commonnessextracting, the use ofextendsThe code doesReuse!)

2.1 Understanding Inheritance

Classes are created in code primarily to abstract things from reality (including properties and methods),

Sometimes there are some correlations between objective things, so there will be certain correlations when they are represented as classes and objects.

For example, designing a class to represent an animal (directly to the code) :

class Animal {
    // Animal names and ages are common!
    public String name;
    public int age;

    // Including eating is also common behavior!
    public void eat(a) {
        System.out.println(name + "eat()"); }}class Dog extends Animal {
    // Reduce the amount of code greatly after extraction!
}

class Bird extends Animal {
    public String wing;

    public void fly(a) {
        System.out.println(name+"fly()"+ age); }}Copy the code

Now, for a class like Animal that’s inherited, we call it a parent class, or a base class, or a superclass, and for a class like Dog or Bird, we call it a subclass, a derived class;

Logically, Dog and Bird are both animals.

Just like a real son inheriting his father’s property,Subclasses also inherit fields and methods from their parent class for code reuse. extendsThe English original meaning is”extension“, and the class inheritance we write can also be understood as code based on the parent class.”extension“;

The Bird class, for example, extends the fly method from Animal.

2.2 Grammar Rules (boring)

Basic syntax:

classA subclassextendsThe parent class{}Copy the code

Note:

  • Use extends to specify the parent class
  • In Java, a subclass can inherit only one parent (languages such as C++/Python support multiple inheritance).

  • A subclass inherits everything from its parent classpublicFields and methods of
  • Private fields and methods of the parent class are not accessible in subclasses

  • An instance of a subclass also contains an instance of its parent class, which can be referenced using the super keyword

Following this brief summary, here’s another question: Come to the conclusion: subclass field with the same name as the superclass fieldPriority access is subclass !

And it’sMemory mapIt goes like this:

2.3 Subclass construction method

Look at a problem: according to the code that represents the animal class aboveAdd a constructor for the parent classWhy does the following error occur?According to the above error, we get the following conclusion:

  • Superclass constructors cannot be inherited by subclasses
  • The constructor of a subclass must call the constructor of its parent class

Also note: when the parent constructor is called

  • The subclass calls the superclass constructor through super (argument list). The statement calling super must be placed on the first line of the subclass constructor
  • If the parent constructor is not displayed in the subclass constructor, the system calls the constructor with no arguments in the parent class by default. If no parameterless constructor is defined in the parent class, compilation error!

So, change it as follows:So with that out of the way, let’sComplete the main classSo let me draw itMemory map(To strengthen the understanding) :

// The code for the main class is as follows:
public class TestDemo {
    public static void main(String[] args) {
        Dog dog = new Dog("Husky".19);
        System.out.println(dog.name);
        dog.eat();

        Bird bird = new Bird("Magpie".18."I want to fly."); System.out.println(bird.name); bird.eat(); bird.fly(); }}Copy the code

2.4 Difference between super and this

I have come across two keywords super and this in my previous study. The blogger made the following summary based on his own knowledge and blog reference:

Super: a reference to a superclass object (which is dependent on the object) cannot be used in static environments (including static variables, static methods, static statement blocks).

  • super(); // Call the constructor of the parent class
  • super.func(); // Call the normal method of the parent class
  • super.data; // Invoke the member properties of the parent class

This: can be understood as a pointer to this object, it represents the name of the current object (in the program is prone to ambiguity, should use this to indicate the current object; If the function has the same name as the member in the class, use this to specify the member variable name.

  • this(); // Call another constructor formed in this class

Points to note and differences summary:

  • super();andthis();The difference is:super();Call the parent constructor from a subclass,this();Call other methods in the same class
  • super();andthis();All need to be placed in the constructorThe first line
  • Sometimes “this” and “super” cannot be in the same constructor, because “this” must call other constructors, and other constructors must have a “super” statement, so having the same statement in the same constructor loses its meaning and the compiler will not pass
  • this(); And super (); Do not use static variables, static methods, and static statement blocks in static environments.

2.5 Access Rights

There are four types of access to fields and methods in Java:

  • Private: accessible from within a class but not from outside
  • Default (also called package access): Access within a class, within a class within the same package, but not within other classes
  • Protected: Accessible from within the class. Subclasses and classes in the same package are accessible, but not from other classes
  • Public: accessible both inside the class and to the caller of the class

importantThis is the one belowThe scope ofGraph:

Private key words (supplementary point) :

Here’s a question:

Are private member variables of the parent class inherited?

The answer to this question is a little fuzzy, some books say it’s inherited;

But some books say not, suggest we use no inheritance of the answer!

Here’s why:

/ / parent class
class A {
    private int a;// Use the private modifier
}
Copy the code
// Subclass this code is wrong
class B extends A { / / inheritance
    public void func(a) {
        System.out.println(this.a);// There is no access to it.}}Copy the code

This knowledge point is written here first, if the latter period has need, it is possible to be added after Baidu!

Feel free to use it in the comments section!

Protected keyword:

We just found that if we make the field private, subclasses cannot access it;

But making it public violates the original purpose of encapsulation;

The protected keyword is the best of both worlds.

  • Protected fields and methods are not accessible to class callers
  • Protected fields and methods are accessible to subclasses of the class and to other classes in the same package

Which one should I use when?

We want classes to be as “encapsulated” as possible, hiding the internal implementation details and exposing only the necessary information to the class caller.

Therefore, we should use as strict access permissions as possible.

For example, if a method can be private, try not to use public.

Alternatively, there is a simple and crude way to do this: make all fields private and all methods public.

This is an abuse of access, and I would like you to think carefully when writing code about the field methods provided by this class (whether they are used by the class itself, the class caller, or the subclass).

2.6 More complex inheritance relationship

It’s an unwritten rule that it’s best to have no more than three levels of inheritance!

Keep in mind that the classes we write are abstractions of real things. However, the real projects we encounter in the company tend to be complex businesses, which may involve a series of complex concepts and require us to use code to express them, so there will be many classes written in our real projects. Relationships between classes are also more complex.

But even so, we don’t want the hierarchy of inheritance between classes to be too complex. We generally don’t want more than three levels of inheritance. If there are too many inheritance layers, you need to consider refactoring your code.

If you want to limit inheritance syntactically, you can use the final keyword!

2.7 Final Keyword

In the past we learned about the final keyword, which represents a constant when modifying a variable or field.

final int a = 10;
a = 20; // Error compiling
Copy the code

The final keyword can also modify classes (called sealed classes), in which case the modified class cannot be inherited!

The function of the final keyword is to restrict classes from being inherited, and “limiting” means “inflexible”.

In programming, being flexible isn’t always a good thing; it can mean being more prone to error.

And what we’re used toThe String classisfinalModified:


3. The polymorphism


There are many forms of one thing.

But don’t say that when the interviewer asks!

Understanding polymorphism is a process!

3.1 Upward Transformation

Based on the above inheritance relationship, we discuss:

public static void main(String[] args) {
        /*Dog Dog = new Dog(" Dog ",20); Animal animal = dog; * /
        
        // Simplify the above code
        Animal animal = new Dog("Prosperous wealth.".23);// Upward transition
        // The parent class refers to the subclass object
    }
Copy the code

The parent class refers to the access member

Here I’m adding a knowledge point that complements inheritance and access,

Then let’s show the code again (for convenience I directly write knowledge points into the code, please note that check) :

/ / Animal classes
class Animal {
    public String name = "Animal";
    public int age;
    protected int count;

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

    public void eat(a) {
        System.out.println(name+" eat()"); }}Copy the code
// The Bird class descends from Animal
lass Bird extends Animal {
    public String wing;
    public String name = "Birds";

    public Bird(String name, int age, String wing) {
        super(name, age);
        this.wing = wing;
    }

    public void fly(a) {
        System.out.println(super.name + "fly()"); }}Copy the code
// Main method of the main class
public static void main(String[] args) {

        Animal animal2 = new Bird("wuya".12."wuya fly!");// There is an upward transition
        animal2.eat();// The eat method can be called

        System.out.println(animal2.name);// Call the name of the parent class

// Attention: key knowledge here!!
// System.out.println(animal2.wing); inaccessible
// Because animal type is animal type
// Only the members of the parent class can be accessed through a reference to the parent class.

    }
Copy the code

When does upward transition take place?

  1. Direct assignment (which is the case above)
public static void main(String[] args) {
        /*Dog Dog = new Dog(" Dog ",20); Animal animal = dog; * /
        
        // Simplify the above code
        Animal animal = new Dog("Prosperous wealth.".23);// Upward transition
        // The parent class refers to the subclass object
    }
Copy the code
  1. As arguments to the function
public class TestDemo2 {

    public static void func(Animal animals) {}public static void main(String[] args) {

        Dog dog = new Dog("Golden retriever".20);
        func(dog);// An upward transition occurs here}}Copy the code
  1. As the return value of the method
 public static Animal fun2(Animal animalss) {
        Dog dog = new Dog("huahua".23);
        return dog;// An upward transition occurs here
    }
Copy the code

3.2 Dynamic Binding

There are two types of polymorphism in Java, run-time polymorphism (dynamic binding) and compile-time polymorphism (static binding)!

Compile-time polymorphism is implemented by overloading, depending on the number of arguments you give, to deduce which function you call!

So what does runtime polymorphism look like? Look down…

First question: Because this is what happensDynamic binding!

Two conditions for dynamic binding to occur:

  • The parent class referencereferenceA subclass object
  • With this superclass reference,Calls override methods with the same parent and subclass names

Note: dynamic binding is the foundation of polymorphism!!

Still a little confused about what this dynamic means at this time, then read on…

Take a look at the following bytecode file:

Before we do that, let’s look at how to open disassembly code in Java. Let’s look at the disassembly code (main method) :We see in disassembly codeI’m calling animal.eat;(eat method of parent class),butRun timeWhy dog.eat() is called;(eat method of the referenced subclass object)?Here it is, here it isCompile time.indeterminacyAt this timeWhose method is called; inRun time.You know whose method to call!

This is called runtime binding, or dynamic binding!

Call the overridden method in the constructor

Look directly at the code:

/ / Animal classes
class Animal {
    public String name = "Animal";
    public int age;

    public Animal(String name,int age) {
        eat();// Dynamic binding also occurs when the parent and subclass override eat methods are called in the parent class!
        this.name = name;
        this.age = age;
    }

    public void eat(a) {
        System.out.println(name+" eat()"); }}Copy the code
//Dog is descended from Animal
class Dog extends Animal {
    public Dog(String name, int age) {
        super(name, age);// Displays the call constructor
    }

    @Override // This is an annotation
    public void eat(a) {
        System.out.println(name+"crazy eat()"); }}Copy the code
// Main method of the main class
public static void main(String[] args) {
        Dog dog = new Dog("wawa".23);// Create an object and run it directly
    }
Copy the code

The running results are as follows: Explanation: theThe parent class calls the eat method overridden by the parent and child classes.So-called dynamic binding also occurs!

Static binding

class Dog {
    public void func(int a) {
        System.out.println("int");
    }

    public void func(int a,int b) {
        System.out.println("int,int");
    }

    public void func(int a,int b,int c) {
        System.out.println("int,int,int"); }}Copy the code
// The main method of the main class:
public static void main(String[] args) {
        Dog dog = new Dog("haha".19);
        dog.func(10);
    }
Copy the code

Here we openPowerShellWindow to view disassembly code: Now what’s happening here is:Static binding!

The function you call is derived from the type and number of arguments you give.

3.3 Method Rewriting

The Override method with the same name as the parent class is Override!

At this point, the rewrite should satisfy the following conditions:

  1. Same method name
  2. Same parameter list (number and type)
  3. Return the same value
  4. It has to be a parent-child case

And note:

  • Static methodCan'trewrite
  • Access-modifier qualifier for a subclassIs greater than or equal toAccess modifier qualifiers for the parent class
  • Methods decorated with private cannot be overridden
  • Methods decorated with final cannot be overridden

But there is a special time (rarely written in books and rarely on exams) :

When overridden, the return value can be different!

But to meet the following conditions:ifYou meet multiple choice questionsThe time,Choose the right oneCan be spicy!

Here’s one thing:

Animal up here returns Animal, Dog returns Dog,

Their return values form a type called covariant type!

If your return value is covariant, we also say it has been overwritten!

3.4 The difference between overwriting and overloading (reordering)

Rewrite (Override) : a subclass inherits the parent class of the original method, but sometimes a subclass and don’t want to inherit a method in the parent class of intact, so the method name and argument list, a return type (with the exception of the return value of a method in a subclass is a subclass of the parent class method return value) are the same, to modify or Override the method body. Namely shell unchanged, core rewrite!

  • The return value of the two methods (except for the special time and subclass of the method return type written above), the method name, and the argument list must be exactly the same (the subclass overrides the parent class’s method).
  • The access level of a subclass method cannot be lower than that of the corresponding method of the parent class
  • An overridden method throws the same exception as an overridden method, or a subclass of it (a subclass exception cannot be larger than its parent).
  • Methods that are private, final, and static cannot be overridden

Overload: Methods with the same name in a class that have different argument lists (different parameter types, different number of arguments, or even different order of arguments) are considered overloaded. At the same time, an overload has no requirement for the return type. It can be the same or different, so it cannot be judged by whether the return type is the same or not.

  • Same method name, different parameter list (parameter order, number, type)
  • Method returns a value of any access modifier

Points to note and differences summary:

  • What rewrite does isPolymorphism at run timeThat’s what overloading doesCompile-time polymorphism
  • Overridden method parameter lists must be the same (in general); Overloaded method argument lists must be different
  • The return type of an overridden method can only be a superclass type or a subclass of the superclass type. Overridden methods do not require a return type

3.5 Downward Transformation

Look at the following code:

public static void main(String[] args) {
        Animal animal3 = new Bird("lala".12."flyyyyy");
        Bird bird = (Bird)animal3;// Forcible conversion
        bird.fly();// Call the fly method here

        // It is not recommended to write this here, sometimes it is wrong (not very safe)!
        // Because not all animals are birds, logic is subversive!

        // You can transition down;
        // The premise is that the reference (animal3) refers to the object (bird) you are going to transition down!
    }
Copy the code

So why is it not very safe?

// This code is wrong!
public static void main(String[] args) {
        Animal animal4 = new Dog("aa".23);
        Bird bird = (Bird)animal4;// A cast exception will be reported
        // Because not all animals are birds!
        bird.fly();
    }
Copy the code

So, to make the downward transition safer, we can first determine if Animal is essentially an instance of Bird, and then convert:

public static void main(String[] args) {
        Animal animal4 = new Dog("aa".23);
        
        if (animal4 instanceof Bird) { // There is no if statement in here
            Bird bird = (Bird)animal4;
            bird.fly();
        }
        // Nothing after run
    }
Copy the code

Instanceof can determine if a reference is an instanceof a class:

If so, return true!

It’s safer to make a downward transition.

3.6 Understand polymorphism

Let’s start with some code:

class Shape {
    public void draw(a) {
        System.out.println("In the printed graph..."); }}Copy the code
class Rect extends Shape {
    @Override
    public void draw(a) {
        System.out.println(♦ ""); }}Copy the code
class Flower extends Shape {
    @Override
    public void draw(a) {
        System.out.println("❀"); }}Copy the code
public class TestDemo1 {

    public static void drawMap(Shape shape) {
        shape.draw();// Dynamic binding (runtime), where the overridden draw method is called
    }

    public static void main(String[] args) {
        // Its classes and those of the following objects are subclasses of Shape for upward transformation!
        Rect rect = new Rect();
        drawMap(rect);
        Flower flower = newFlower(); drawMap(flower); }}Copy the code

Here’s a simple definition:

Through a reference, calling a draw method (the method overridden by the parent and subclasses) will have a different representation (depending on whose object is referenced). This is polymorphic!

The main premise of polymorphism is that you must transition up and call a superclass method (subclass overrides, call a superclass)!

What are the benefits of using polymorphism?

1: The cost of using a class is further reduced for class callers

  • Encapsulation is the idea that the caller of a class does not need to know the implementation details of the class
  • Polymorphism allows the caller of a class to know that the class doesn’t even have to know what type the class is, just that the object has a method, right

Therefore, polymorphism can be understood as the next step in encapsulation, making it even cheaper for class callers to use classes!

This is in line with the original purpose of “managing code complexity” in Codex!

2: Can reduce the “cyclomatic complexity” of code, avoid using a lot of if-else

Look at the code:

// Not based on polymorphism
public static void main3(String[] args) {
        Rect rect = new Rect();
        Flower flower = new Flower();
        Triangle triangle = new Triangle();

        String[] shapes = {"triangle"."rect"."triangle"."rect"."flower"};
        for (String s : shapes) {
            if(s.equals("triangle")) {
                triangle.draw();
            }else if(s.equals("rect")) {
                rect.draw();
            }else{ flower.draw(); }}}Copy the code
// Based on polymorphisms:
// It is obvious that the code is more advanced and the amount is less!
public static void main4(String[] args) {
        Rect rect = new Rect();
        Flower flower = new Flower();
        Triangle triangle = new Triangle();

        Shape[] shapes = {triangle,rect,triangle,rect,flower,};
        for(Shape shape : shapes) { shape.draw(); }}Copy the code

What is cyclomatic complexity?

Cyclomatic complexity is a way of describing the complexity of a piece of code, which is simpler and easier to understand if it is laid out. If there are many conditional branches or loops, it is considered more complex to understand.

Therefore, we can simply count the number of conditional and loop statements in a piece of code. This number is called “cyclomatic complexity”. If a method is too cyclomatic, we need to consider refactoring.

Different companies have different specifications for the cyclomatic complexity of their code, generally less than 10.

3. Stronger scalability

If you want to add a new shape, using a polymorphic way of code change is cheaper!

class Triangle extends Shape{
    @Override
    public void draw(a) {
        System.out.println("Delta"); }}Copy the code

For the caller to create a new instance of the class, the cost of change is low,

For non-polymorphic cases, if-else in drawShapes needs to be modified at a higher cost.

4. An abstract class

4.1 Understand abstract classes

The article writes here, actually is a little flaw, do not know everybody has found! Dog head for life!!

Let’s go back to the code that prints the graph (parent class) :

class Shape {
    public void draw(a) {
        System.out.println("In the printed graph..."); }}Copy the code

So let’s think about it a little bit,

System.out.println(” println “) ); This piece of code is meaningless, because it’s just class inheritance and method rewriting (no real work)!

Can the following code be written like this?

// This is not true
class Shape {
    public void draw(a);
}
Copy the code

Then we have the following:

// The abstract keyword is added to indicate that this is an abstract class
abstract class Shape {
    // This is an abstract method
    abstract public void draw(a);// Abstract methods have no method body (no {}, can't execute concrete code)!
    
    // Also note that classes that contain abstract methods are called abstract classes
}
Copy the code

4.2 Grammar Rules

  1. Abstract classes cannot be instantiated directly (an error will be reported)

2. Abstract classes can have ordinary methods and members 3. The ordinary class inherits the abstract class, in which all the abstract methods of the abstract class must be overridden (which can be overridden and called) 4. Abstract methods cannot beprivateModification of the

Not only that, there are some special rules!

  1. If an abstract class B inherits abstract class A, then this abstract class A can not implement abstract methods of abstract class A!
  2. On the basis of the inheritance relationship above, ordinary class C inherits abstract class B, then the abstract methods in A and B must be overridden!
  3. Abstract classes and methods cannot befinalModified!

The code looks like this:

abstract class A {
    abstract public void draw(a);// Abstract methods
}
Copy the code
abstract class B extends A{ // This is inherited from Shape
    public abstract void funcA(a);// This is also an abstract method
    // Note: an abstract class B inherits an abstract class A. This abstract class A does not implement the abstract methods of abstract class A.
}
Copy the code
class C extends B {
// On the basis of the above inheritance relationship, ordinary class C inherits abstract class B, so the abstract methods in A and B must be overridden!
    @Override
    public void funcA(a) {}@Override
    public void draw(a) {}}Copy the code

4.3 The role of Abstract classes

Abstract classes exist in order to be inherited!

Some people might say that ordinary classes can be inherited and ordinary methods can be overridden, so why use abstract classes and methods?

For scenarios using abstract classes like the code above, the actual work should not be done by the parent class, but by the child class,

If you accidentally use the parent class, the compiler will not give you an error!

In fact, there is a warning error function, the parent class is abstract class will be in the instantiation of the error, let us find the problem as soon as possible!

5. The interface

This section is very tedious knowledge (syntax), any knowledge is in the code comments (easy to understand directly)!

Knowledge points are in the code comments!

Knowledge points are in the code comments!

Knowledge points are in the code comments!

// This is an abstract class that leads to the following interface!
abstract class Shape {
    abstract public void draw(a);
}
Copy the code

Interfaces are a step up from abstract classes!

An abstract class can also containNon-abstract methods and fields;

And the methods contained in the interface areAbstract methods, fields can only containStatic constants!

5.1 Understanding interfaces and Simple Syntax rules

// Define an interface using interface
interface IShape {
    //abstract public void draw(); // We can do this without using abstract public.
    // And note that all methods in the interface are pubilc!
    void draw(a);// Abstract methods

    // Common methods in interfaces cannot be implemented concretely!
    //public void func() {// This method is wrong!
    //} //error

    // To implement this method, use the default keyword!
    default public void func(a) {
        System.out.println("Common methods in interfaces...");
    }

    // Interface can have static methods!
    public static void funcStatic(a) {
        System.out.println("Static methods in the interface..."); }}Copy the code

Interface summary:

  • Methods in interfaces must be abstract methods, so you can omit abstract
  • The method in the interface must be public, so you can omit public
// The relationship between a class and an interface is implemented through the implements keyword!
class Rect implements IShape {
    // When a class implements an interface, it must override the abstract methods in the interface!
    @Override
    public void draw(a) {
        System.out.println(♦ "");
    }
    
    @Override
    public void func(a) {
        System.out.println("Override default methods in interfaces."); }}class Flower implements IShape {
    @Override
    public void draw(a) {
        System.out.println("❀"); }}class Triangle implements IShape {
    @Override
    public void draw(a) {
        System.out.println("Delta"); }}class Cycle implements IShape {
    @Override
    public void draw(a) {
        System.out.println("Low"); }}Copy the code
// Test main class:
public class TestDemo3 {

    public static void drawMap(IShape iShape) {
        iShape.draw();// Dynamic binding (runtime), where the overridden draw method is called
    }

    public static void main(String[] args) {

        //IShape iShape = new IShape(); // Error, interface cannot be instantiated!
        IShape iShape = new Rect();// But upward transformation can occur!
        iShape.draw();

        // Its classes and those of the following objects are subclasses of Shape for upward transformation!
        Rect rect = new Rect();
        Flower flower = newFlower(); drawMap(rect); drawMap(flower); }}Copy the code

Summary:

  • Interfaces cannot be instantiated separately
  • It is also possible to create a reference to the interface when invoked, corresponding to an instance of a subclass
  • Rect uses implements to inherit the interface, which means “implement” instead of “extend”

Extensions (extends) and implementation (implementsDistinguish between:

  1. To extend is to extend a function that is already in place
  2. An implementation is something that currently has nothing and needs to be constructed from scratch

5.2 Implement multiple interfaces and other syntax rules

Again, go straight to the code:

// Define interface IA
interface IA {
    // Interface member variables, default is public static final!
    //public static final int a = 10; // It can be written like this.
    int A = 10;// Is a constant

    void funcA(a);// The default is pubilc abstract!
}
Copy the code
// Define interface IB
interface IB { 
    void funcB(a);
}
Copy the code
// Define abstract class B
abstract class B {
    // Abstract class B
}
Copy the code

Sometimes we need a class that inherits from more than one parent class.

This is done in some programming languages through multiple inheritance,

However, only single inheritance is supported in Java, and a class can extend only one parent class!

But you can implement multiple interfaces at the same time and achieve similar effects of multiple inheritance!

// The following class A inherits abstract class B (normal class can also), but only single-inheritance!
// Multiple interfaces can also be implemented, separated by commas!
class A extends B implements IA.IB {
    @Override
    public void funcA(a) { When a class implements an interface and overrides a method, the method must be pubilc!
                          // If pubilc permission is not more strict, so can not overwrite
        System.out.println("Override funcA");
        System.out.println(A);// You can also access things in the interface!
    }

    @Override
    public void funcB(a) {
        System.out.println("Override funcB"); }}Copy the code

What are the benefits of this design?

Keep the benefits of polymorphism in mind and let programmers forget about types.

With interfaces, users of classes don’t have to worry about specific types,

Instead, you focus on whether a class has certain capabilities.

Additional tips:

  1. When we create interfaces, they are usually named with a capital letter I
  2. Interfaces are usually named using “adjective” wordsWith XXX features)
  3. Ali coding specification, interface methods and attributes do not add any modifier symbols, keep the code concise

5.3 Inheritance between Interfaces

As mentioned earlier, the relationship between a class and an interface is the implements operation.

The question I would like to ask is:

theninterfaceandinterfaceWhat kind of relationship does it have?

interface IA1 {
    void funcA(a);
}

// Interfaces and interfaces can use extends to manipulate their relationships. In this case, this means: extend.
interface IB1 extends IA1 {
    void funcB(a);
}

class C implements IB1 {
    @Override
    public void funcB(a) {
        System.out.println("Rewriting B's is not enough!");
    }

    @Override
    public void funcA(a) {
        System.out.println("And rewrite A's!"); }}Copy the code

One interface, IB1, extends the functionality of another, IA1, through extends.

A class C implements IB1 via implements,

Now the method that you’re rewriting is not justAbstract methods for IB1And he had beenFunctions extended from IA1 interface (Methods).

5.4 Interface Examples

In this summary to introduce you to three commonly used interfaces!

Comparable interface

Directly on the code:

class Student {
    public int age;
    public String name;
    public double score;

    public Student(int age, String name, double score) {
        this.age = age;
        this.name = name;
        this.score = score;
    }

    @Override
    public String toString(a) {
        return "Student{" +
                "age=" + age +
                ", name='" + name + '\' ' +
                ", score=" + score +
                '} '; }}public class TestDemo7 {

    public static void main(String[] args) {
        Student[] students = new Student[3];
        students[0] = new Student(12."huahua".56);
        students[1] = new Student(23."wewe".34);
        students[2] = new Student(32."rous".78);

        System.out.println(Arrays.toString(students));
        Arrays.sort(students);// There is a problem with the sort methodSystem.out.println(Arrays.toString(students)); }}Copy the code

Running as above will cause an error, because there is nothing to sort by (there is nothing to compare)!

You can look at the underlying code more interested!The modified code looks like this:

// Implement a Comparable interface directly
class Student implements Comparable<Student> {
    public int age;
    public String name;
    public double score;

    // Select * from 'age' where 'age' = 'age';
    @Override
    public int compareTo(Student o) { // Whoever calls this method is this
        /*if(this.age > o.age) { return 1; }else if(this.age == o.age) { return 0; }else { return -1; } * /

        // Simpler implementations (from small to large)
        return this.age - o.age;
    }

    public Student(int age, String name, double score) {
        this.age = age;
        this.name = name;
        this.score = score;
    }

    @Override
    public String toString(a) {
        return "Student{" +
                "age=" + age +
                ", name='" + name + '\' ' +
                ", score=" + score +
                '} '; }}public class TestDemo7 {

    // Learn how to use compareTo!
   /* public static void main(String[] args) { Student student1 = new Student(98,"huahua",56); Student student2 = new Student(45,"wewe",34); System.out.println(student1.compareTo(student2)); // a number greater than zero}*/

    public static void main(String[] args) {
        Student[] students = new Student[3];
        students[0] = new Student(12."huahua".56);
        students[1] = new Student(45."wewe".34);
        students[2] = new Student(32."rous".78);

        System.out.println(Arrays.toString(students));
        Arrays.sort(students);// The default order is from smallest to largest
        System.out.println(Arrays.toString(students));
    }
Copy the code

To sum up: if you want to do custom type size comparisons, make sure you implement interfaces that can be compared!

The Comparable interface has a disadvantage, however, if you want to change the score comparison code to a larger number of changes!

Disadvantages: The intrusion of the class is very strong, once written, dare not easily change!

The Comparator interface

So, there’s a better way!

Is the comparator, directly paste code:

class Student {
    public int age;
    public String name;
    public double score;

    public Student(int age, String name, double score) {
        this.age = age;
        this.name = name;
        this.score = score;
    }

    @Override
    public String toString(a) {
        return "Student{" +
                "age=" + age +
                ", name='" + name + '\' ' +
                ", score=" + score +
                '} '; }}// There is a shortcut Alt +7 to see what methods are inside!

class AgeComparator implements Comparator<Student> {
    @Override
    public int compare(Student o1, Student o2) {
        returno1.age - o2.age; }}class Score implements Comparator<Student> {
    @Override
    public int compare(Student o1, Student o2) {
        return (int)(o1.score - o2.score);// Cast to int}}// The main interface used is this!
// This is the second common interface.
class NameComparator implements Comparator<Student> {
    @Override
    public int compare(Student o1, Student o2) {
        returno1.name.compareTo(o2.name); }}public class TestDemo7 {

    // Learn how to use compareTo!
   /* public static void main(String[] args) { Student student1 = new Student(98,"huahua",56); Student student2 = new Student(45,"wewe",34); // Learn how to use compareTo! // System.out.println(student1.compareTo(student2)); // Here is a number greater than zero // compare is used! AgeComparator ageComparator = new AgeComparator(); System.out.println(ageComparator.compare(student1,student2)); // a number greater than zero}*/

    public static void main(String[] args) {
        Student[] students = new Student[3];
        students[0] = new Student(12."huahua".56);
        students[1] = new Student(45."wewe".34);
        students[2] = new Student(32."rous".78);

        System.out.println(Arrays.toString(students));// Print before sort
        AgeComparator ageComparator = new AgeComparator();
        Score score = new Score();
        NameComparator nameComparator = new NameComparator();
        // Different comparators can be used here!
        Arrays.sort(students,nameComparator);// Here is ageComparator (pass is a comparator), recommend to look at the source!
        System.out.println(Arrays.toString(students));// Sort and print}}Copy the code

Therefore, we can deduce that the advantage of comparator is: flexible!

Very weak on class invasions!

The Comparable or Comparator interface will depend on your business.

Cloneable interface and deep copy and shallow copy

/** * * * We continue to explore how to create objects: * 1: new keyword * 2: implement Cloneable interface */

// To clone a class, implement the Cloneable interface
class Person implements Cloneable{
    public int age;

    public void eat(a) {
        System.out.println("Eatting!");
    }

    @Override
    public String toString(a) {
        return "Person{" +
                "age=" + age +
                '} ';
    }

    /** * The clone method is a special one. It is implemented in C/C++ and must be override@return
     * @throws CloneNotSupportedException
     */
    @Override
    protected Object clone(a) throws CloneNotSupportedException {
        return super.clone();// There is no concrete rewrite implementation, it is the C/C++ code called!}}public class Main {

    public static void main(String[] args) throws CloneNotSupportedException {
	Person person = new Person();
    person.age = 99;// Here is the assignment
    Person person1 = (Person) person.clone();// In memory, the age of the copy is 99!
        // If you change the value of copy (person1), it will not affect the value of person!
    }

    // It is not the method that determines whether deep copy or shallow copy, but the implementation of the code!

    // Clone is not a deep copy.
    // However, we need to find a way to make it deep copy!
}
Copy the code

Its memory map looks like this:

Before we talk about deep copy, let’s take a look at the Cloneable interface!

weClick on the Cloneable interface to see the code:Here comes an interview question:Do you knowThe Cloneable interface? Why is this interface a null interface? Have a purpose?

It’s very simple, because this interface is empty, so it’s empty,

But it is a flag interface that indicates that the current class can be cloned!

Here's how this interface works:

When used for the first time, it will report an error, need to throw exceptions to solve!

Hold down theALT+ENTER, just click options!

Read on:

/** * how to deep copy! * Below will be above the code, sublimate! * Learn what shallow copy is before you do! * /
class Money implements Cloneable{
    public double m = 12.5;

    @Override
    protected Object clone(a) throws CloneNotSupportedException {
        return super.clone(); }}class Person implements Cloneable{
        public int age;
        public Money money = new Money();

        public void eat(a) {
            System.out.println("Eatting!");
        }

        @Override
        public String toString(a) {
            return "Person{" +
                    "age=" + age +
                    '} ';
        }

        @Override
        protected Object clone(a) throws CloneNotSupportedException {
            //return super.clone(); // There is no concrete rewrite implementation, it is the C/C++ code called!
            Person tmp = (Person)super.clone();
            tmp.money = (Money) this.money.clone();
            return tmp;
            // The above operation is a deep copy!}}public class Main {

    public static void main(String[] args) throws CloneNotSupportedException {
        Person person = new Person();
        Person person2 = (Person)person.clone();
        System.out.println(person.money.m);
        System.out.println(person2.money.m);
        // Print out the same value, why? Look at the memory map!
        System.out.println("= = = = = = = = = = = = = = = = = = = = =");
        person2.money.m = 99.99;
        System.out.println(person.money.m);
        System.out.println(person2.money.m);
        // Print out the same value, why? Look at the memory map!

        // This is a shallow copy!
        // How to deep copy?

        // It is not the method that determines whether deep copy or shallow copy, but the implementation of the code!}}Copy the code

Its memory map looks like this:

How do I deep copy it?

// Rewrite this class!
 @Override
        protected Object clone(a) throws CloneNotSupportedException {
// return super.clone(); // There is no concrete rewrite implementation, it is the C/C++ code called!
            Person tmp = (Person)super.clone();
            tmp.money = (Money) this.money.clone();
            return tmp;
            // The above operation is a deep copy!}}Copy the code

Its memory map looks like this:

A very important sentence:It is not the method that determines whether to make a deep copy or a shallow copy, but the implementation of the code!

5.5 The difference between Abstract Classes and interfaces

Abstract class: WHEN a class is modified by abstract, it is called abstract.

  • Abstract classes cannot be instantiated directly (an error will be reported)

  • Abstract classes can have ordinary methods and members

  • The ordinary class inherits the abstract class, in which all the abstract methods of the abstract class must be overridden (which can be overridden and called)

  • Abstract methods cannot beprivateModification of the

  • If an abstract class B inherits abstract class A, then this abstract class A can not implement abstract methods of abstract class A!

  • On the basis of the inheritance relationship above, ordinary class C inherits abstract class B, then the abstract methods in A and B must be overridden!

  • Abstract classes and methods cannot befinalModified!

Interface: In a class, methods with the same name that have different argument lists (different parameter types, different number of arguments, or even different order of arguments) are considered overloaded. At the same time, an overload has no requirement for the return type. It can be the same or different, so it cannot be judged by whether the return type is the same or not.

  • Interfaces cannot be instantiated separately
  • The methods contained in the interface areAbstract methods, fields can only containStatic constants!
  • A common method in an interface cannot have a concrete implementation. If it does, it must be decorated with the default keyword!
  • An interface can have a static method, and that static method can have a method body
  • Methods in interfaces must be abstract methods, so you can omit abstract
  • The method in the interface must be public, so you can omit public

Points to note and differences summary:

  • Cannot be instantiated individually
  • Abstract classes inherit abstract classes using the extends keyword; Subclasses implement the interface using the keyword implements
  • Abstract methods can have public, protected, and default modifiers; The default modifier for interface methods is public; no other modifier can be used.
  • Abstract classes can only be inherited; Interfaces can be implemented multiple times
  • Abstract classes can have ordinary methods and members; The methods contained in the interface are abstract, and the fields can only contain static constants!

The full text end

This is the end of this article, during the visit of a large number of literature, including a variety of courseware, blogs, documents and so on!

By the way, there is a link on the left side of the object oriented training mentioned earlier!

Writing is not easy, and your support is my biggest motivation! Kneel beg three even!!

Tired!