Hãy xem xét đoạn mã sau (mã 2).
abstract class Vehicle{
abstract void park();
}
class Demo{
static class Car extends Vehicle {
int speed;
void park(){
System.out.println("Parking for cars...");
}
}
public static void main(String args[]){
Vehicle v1=new Car();
v1.park();
}
}
Không có gì ngạc nhiên khi đoạn mã trước đó không có lỗi trình biên dịch.
Xe mở rộng Xe và Xe không phải là trừu tượng. Do đó bạn có thể khởi tạo nó.
Cho phép xem những gì sẽ xảy ra khi 2 mã được biên dịch:
javac *.java
list .class files
Demo$Car.class Demo.class Vehicle.class
Và đây là những gì sẽ xảy ra khi các mã trong câu hỏi (mã 1) được biên soạn:
javac *.java
list .class files
Demo$1.class Demo.class Vehicle.class
Chúng tôi nhận được cùng một ngoại trừ chúng ta có được Demo $ 1.class trong mã 1 và Demo $ Car.class trong mã 2.
Điều đó xảy ra vì mã 1 thực sự đang tạo một lớp kế thừa từ Xe. Một cái gọi là lớp vô danh. Lớp học không có tên (*) nhưng nó vẫn là một lớp học chính thức được thừa hưởng từ Xe và có thể được khởi tạo ngay khi Xe có thể được khởi tạo.
Mã này:
Vehicle v1=new Vehicle(){
là KHÔNG instantiating một đối tượng của lớp Vehicle. Nó là instantiating một đối tượng của một lớp mà kế thừa từ xe mà không có tên.
(*) Thực ra nó có tên. Tên của nó là "1 in Demo" hay còn gọi là Demo $ 1. JVM cần một tên để có thể chạy nó, bạn không thể chỉ cần nói cho JVM chạy một cái gì đó mà không nói cho nó những gì để chạy. Tên là tên không phải là tên hợp lệ của một lớp; không thể đặt tên một lớp là 1. Đây là do dessign vì nó đảm bảo rằng các tên lớp đồng nghĩa sẽ không đụng độ với các tên lớp bình thường.
Nguồn
2015-09-05 06:21:56
Bạn có thể muốn bao gồm các lệnh Terminal của bạn chỉ dành cho hệ thống * nix. –
Ok, sẽ làm rõ điều đó. javac là phổ biến đối với bất kỳ nền tảng nào với JDK. –