CodeGym /Blog Java /Ngẫu nhiên /Instanceof và Kế thừa trong Java

Instanceof và Kế thừa trong Java

Xuất bản trong nhóm
CHÀO! Trong các bài học trước, chúng ta đã làm quen sơ qua với khái niệm kế thừa. Hôm nay, chúng ta sẽ chạm vào chủ đề này một lần nữa, nhưng một lần nữa không quá sâu. Chúng tôi vẫn sẽ có một bài học chi tiết hơn về điều này trong tương lai. Hôm nay chúng ta sẽ xem nhanh một vài ví dụ thực tế và làm quen với một toán tử thú vị trong Java.

Di sản

Vậy thừa kế là gì? instanceof và Kế thừa 101 - 1 Kế thừa là một cơ chế lập trình (kể cả trong Java) cho phép bạn khai báo một lớp mới dựa trên một lớp hiện có. Sau đó, lớp dẫn xuất có quyền truy cập vào các trường và phương thức của lớp cha. Tại sao chúng ta cần điều này? Chà, hãy tưởng tượng rằng bạn cần tạo một số lớp ô tô trong một chương trình: Xe tải, Xe đua, Xe sedan, Xe bán tải, v.v. Ngay cả trước khi viết bất kỳ mã nào, bạn biết chắc rằng tất cả các lớp này đều có nhiều điểm chung: tất cả ô tô đều có một kiểu tên, năm sản xuất, kích thước động cơ, tốc độ tối đa, v.v. (chưa kể đến việc chúng đều có chung bánh xe và các bộ phận khác). Trong tình huống này, bạn có thể:
  • Tạo các trường này trong mỗi lớp (thêm chúng vào mỗi lớp ô tô mới khi bạn tạo nó)
  • Mang các trường chung cho tất cả các ô tô vào một Carlớp cha, sau đó sử dụng từ khóa mở rộng để dẫn xuất tất cả các lớp cho các loại ô tô cụ thể từ Carlớp đó.
Đương nhiên, tùy chọn thứ hai thuận tiện hơn nhiều:

public class Car {

   private String model;
   private int maxSpeed;
   private int yearOfManufacture;

   public Car(String model, int maxSpeed, int yearOfManufacture) {
       this.model = model;
       this.maxSpeed = maxSpeed;
       this.yearOfManufacture = yearOfManufacture;
   }
}

public class Truck extends Car {

   public Truck(String model, int maxSpeed, int yearOfManufacture) {
       super(model, maxSpeed, yearOfManufacture);
   }
}

public class Sedan extends Car {
   public Sedan(String model, int maxSpeed, int yearOfManufacture) {
       super(model, maxSpeed, yearOfManufacture);
   }
}
Ở mức tối thiểu, chúng ta tránh được sự trùng lặp mã không cần thiết (và chúng ta nên luôn cố gắng đạt được điều đó khi viết chương trình). Ngoài ra, chúng tôi có cấu trúc lớp đơn giản và dễ hiểu, với tất cả các trường chung cho tất cả các ô tô được hợp nhất thành một lớp. Nếu xe tải có bất kỳ trường đặc biệt nào mà những chiếc xe khác không có, chúng có thể được khai báo trong Trucklớp. Điều tương tự cũng xảy ra với các phương pháp. Tất cả các ô tô đều có một số hành vi chung có thể được mô tả bằng các phương thức, ví dụ: khởi động ô tô, tăng tốc/phanh, v.v. Các phương thức chung này có thể được hợp nhất vào lớp cha Carvà mỗi loại ô tô cụ thể có thể định nghĩa các hành động duy nhất của nó trong các lớp dẫn xuất của chúng .

public class Car {

   public void gas() {
       // Accelerate
   }

   public void brake() {
       // Brake
   }
}


public class F1Car extends Car {

   public void pitStop() {
      
       // Only race cars make pit stops
   }

   public static void main(String[] args) {
      
       F1Car formula1Car = new F1Car();
       formula1Car.gas();
       formula1Car.pitStop();
       formula1Car.brake();
   }
}
Chúng tôi đã thêm các phương thức phổ biến cho tất cả các ô tô vào Carlớp. Nhưng, hãy nhìn vào F1Carhạng xe đại diện cho những chiếc xe đua "Công thức 1". Điểm dừng pit (điểm dừng để bảo dưỡng ô tô khẩn cấp) chỉ được thực hiện trong các cuộc đua, vì vậy chúng tôi đã thêm chức năng cụ thể này vào lớp dẫn xuất có liên quan. instanceof và Kế thừa 101 - 2

toán tử instanceof

Trong Java, có một toán tử đặc biệt, instanceof , để kiểm tra xem liệu một đối tượng có được tạo dựa trên một lớp cụ thể hay không. Nó trả về true hoặc false tùy thuộc vào kết quả kiểm tra. Hãy xem cách nó hoạt động bằng cách sử dụng các lớp trong ví dụ về ô tô của chúng ta:

public class Truck extends Car {

   public static void main(String[] args) {

       Truck truck = new Truck();
       System.out.println(truck instanceof Car);
   }
}
Đầu ra: true Toán instanceoftử trả về true , vì chúng ta có một Truckđối tượng và tất cả các xe tải đều là ô tô. Lớp Truckcó nguồn gốc từ Carlớp. Tất cả các xe tải được tạo dựa trên cha chung, Carlớp. Hãy xem kỹ cách instanceoftoán tử được sử dụng. Bạn viết nó mà không có dấu chấm, vì nó là một toán tử, không phải là một phương thức ("đối tượng thể hiện của Lớp”). Hãy thử một cách khác:

public static void main(String[] args) {

   Car car = new Car();
   System.out.println(car instanceof Truck);
}
Kết quả: false Lớp Car(và các đối tượng ô tô) không xuất phát từ Trucklớp. Tất cả xe tải đều là ô tô, nhưng không phải ô tô nào cũng là xe tải. Carcác đối tượng không dựa trên Trucklớp. Một ví dụ nữa:

public static void main(String[] args) {

   Car car = new Car();
   Truck truck = new Truck();
   System.out.println(car instanceof Object && truck instanceof Object);
}
Đầu ra: Đúng Ở đây logic cũng đơn giản: tất cả các lớp trong Java, kể cả các lớp bạn tạo, đều xuống từ lớp đó Object(mặc dù bạn không viết "extends Object"—nó đã được ngụ ý). Làm thế nào và khi nào điều này sẽ hữu ích? Toán instanceoftử được sử dụng phổ biến nhất khi ghi đè equals()phương thức. Ví dụ: đây là cách equalsphương thức được triển khai trong Stringlớp:

public boolean equals(Object anObject) {
   if (this == anObject) {
       return true;
   }
   if (anObject instanceof String) {
       String anotherString = (String) anObject;
       int n = value.length;
       if (n == anotherString.value.length) {
           char v1[] = value;
           char v2[] = anotherString.value;
           int i = 0;
           while (n-- != 0) {
               if (v1[i] != v2[i])
                       return false;
               i++;
           }
           return true;
       }
   }
   return false;
}
Trước khi so sánh a Stringvới đối tượng đã truyền, phương thức sẽ kiểm tra xem đối tượng có phải là một chuỗi không? Chỉ khi đó nó mới bắt đầu so sánh các thuộc tính của hai đối tượng. Nếu thử nghiệm này không tồn tại, bất kỳ đối tượng nào có trường giá trịđộ dài đều có thể được chuyển đến phương thức và được so sánh với Chuỗi, tất nhiên, điều này sẽ sai.
Bình luận
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION