2015-09-05 8 views
5

Es gibt keine Möglichkeit, ein Objekt zu erstellen, das abstrakte Klasse verwendet. Bei Verwendung der anonymen inneren Klasse ist es jedoch möglich, den folgenden Code auszuführen. Und nicht nur das start() Methode ist nicht zugänglich, weshalb ist der Grund für die Ausführung des folgenden Programms ohne Angabe von Kompilierungsfehler und was ist der Mechanismus für den Zugriff auf start() Methode.Ist es möglich, abstrakte Klasse mit anonymer innerer Klasse und Mechanismus zu instanziieren, um auf Methode innerhalb davon zuzugreifen

abstract class Vehicle{ 
     abstract void park(); 
    } 

    class Demo{ 
     public static void main(String args[]){ 
      Vehicle v1=new Vehicle(){ 
       int speed; 
       void park(){ 
        System.out.println("Parking for cars..."); 
       } 
       void start(){ 
        System.out.println("Start..."); 
       } 
      }; 
      v1.park(); 
     } 
    } 

Antwort

6

Betrachten Sie das folgende Stück Code (Code 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(); 
    } 
} 

Es ist keine Überraschung, dass das vorherige Stück Code keine Compiler-Fehler gibt.
Auto erstreckt sich Fahrzeug und Auto ist nicht abstrakt. Daher können Sie es instanziieren.

Mal sehen, was passiert, wenn Code 2 kompiliert wird:

javac *.java 
list .class files 
Demo$Car.class Demo.class Vehicle.class 

Und das ist, was passiert, wenn der Code in der Frage (Code 1) kompiliert wird:

javac *.java 
list .class files 
Demo$1.class Demo.class Vehicle.class 

Wir bekommen die gleiche außer wir bekommen Demo $ 1. Klasse in Code 1 und Demo $ Car.class in Code 2.
Das passiert, weil Code 1 tatsächlich eine Klasse erstellt, die von Vehicle erbt. Eine sogenannte anonyme Klasse. Die Klasse hat keinen Namen (*), aber sie ist immer noch eine vollwertige Klasse, die von Fahrzeug erbt und instanziiert werden kann, genau wie Auto instanziiert werden kann.

Dieser Code:

Vehicle v1=new Vehicle(){ 

ist NICHT ein Objekt der Klasse Vehicle Instanziierung. Es instanziiert ein Objekt einer Klasse, die von Vehikel erbt, das keinen Namen hat.

(*) Eigentlich hat es einen Namen. Sein Name ist "1 in Demo" alias Demo $ 1. Die JVM benötigt einen Namen, um sie ausführen zu können. Sie können der JVM nicht einfach sagen, dass sie etwas ausführen soll, ohne ihr mitzuteilen, was sie ausführen soll. Der Name ist einer, der kein sintaktisch gültiger Name für eine Klasse ist; kann eine Klasse nicht als 1 bezeichnen. Dies ist durch das Design, da es sicherstellt, dass anonyme Klassennamen nicht mit normalen Klassennamen kollidieren.

+0

Möglicherweise möchten Sie Ihre Terminal-Befehle nur für * nix-Systeme verwenden. –

+0

Ok, werde das klären. javac ist jedoch für jede Plattform mit JDK üblich. –

4

Dies ist genau die Idee in abstrakten Klassen. Sie können die abstrakte Klasse nicht instanziieren, aber Sie können jede Unterklasse instanziieren, die die abstrakten Methoden implementiert. Solche Unterklassen können konkrete Klassen oder anonyme Klassen sein, wie Sie hier haben, also kein Grund für diesen Code nicht

1

Anonymous class bedeutet, dass Sie vor Ort erklärt haben class in Ihrem Demo zu kompilieren. Anonyme Klasse ist ein Ausdruck, der die Implementierung von abstrakten Methoden haben kann. Hauptsächlich ist die anonyme Klasse eine lokale Implementierung von interface oder abstractclass, die die Implementierung abstrakter Methoden und die gleiche Art der Implementierung abstrakter Methoden der abstrakten Klasse enthalten muss. Kurz gesagt, können Sie abstract Klasse mit anonymer Klasse instanziieren.

Hier deklarieren Sie eigentlich Ihre gesamte Klasse Vehicle als anonyme Klasse in Ihrer Demo mit erforderlicher Implementierung. Beachten Sie hier, dass Sie Demo$1.class Datei nach dem Kompilieren der Demo Klasse, die eine anonyme Klasse und Implementierung Ihrer Vehicle in Demo ist.

1

Obwohl Sie ein neues Fahrzeug() schreiben, aber keine Instanz der Fahrzeugklasse erstellen. Erzeugt eine Instanz des Subtyps des Fahrzeugs, die keinen Namen hat

1

Es gibt keine Möglichkeit, ein Objekt mithilfe der abstrakten Klasse zu erstellen. Bei Verwendung der anonymen inneren Klasse ist es jedoch möglich, den folgenden Code auszuführen. Was ist der Grund dafür, folgendes Programm auszuführen, ohne einen Kompilierungsfehler zu geben?

Der Code läuft, weil Sie nicht instanziieren ein Objekt direkt aus dem abstract class sind. Wenn Sie eine anonyme Klasse von abstract class oder interface erstellen erstellen Sie eigentlich eine neue Klasse erstreckt/Umsetzung zum abstract class oder interface.

Es spielt keine Rolle, ob Sie eine innere Klasse verwenden oder nicht.


Kurz gesagt, wenn Sie eine anonyme Klasse zu erstellen, ist es die neue „namenlos“ Klasse, die die abstrakte Klasse erweitert instanziiert wird!