2016-07-14 148 views
5

In tutti i tutorial di parole chiave super che ho trovato online, è difficile ottenere degli esempi più vicini al seguente. La mia domanda:Java - super parola chiave nella nuova discussione Runnable - fa riferimento al metodo non statico attraverso la classe

  1. Qual è la differenza tra Tracker.super.track(event); e test.parent.Tracker.track(event);?

  2. Perché il primo funziona?

  3. A cosa si riferisce Tracker.super? Un oggetto o una classe?

sottoclasse:

package test; 

public class Tracker extends test.parent.Tracker { 


@Override 
    public void track(final Event event) { 
    Executor.execute(new Runnable() { 
     public void run() { 
      Tracker.super.track(event); //this works!! why?? 
      super.track(event); // compile error: cannot resolve 
      test.parent.Tracker.track(event); //compile error: can only reference static method 
     } 
    }); 
    } 

} 

super-classe

package test.parent; 

public abstract class Tracker { 

public void track(Event event) {} 

} 

Aggiornamenti Riferimento:

In jls8, 15.11.2

"Supponiamo che l'espressione di accesso ai campi T.super.f appaia all'interno della classe C, e la superclasse immediata della classe denotata da T sia una classe il cui nome completo sia S. Se f in S è accessibile da C, allora T. super.f è trattato come se fosse stata l'espressione this.f nel corpo della classe S. Altrimenti, si verifica un errore in fase di compilazione.

Così, T.super.f può accedere al f campo che è accessibile in classe S, anche se tale campo è nascosto da una dichiarazione di un campo f in classe T.

È una a tempo di compilazione errore se la classe attuale non è una classe interna della classe T o T stessa ".

+0

'System.out.println (Tracker.class.getName()); ' –

+0

@ElliottFrisch Che cosa significa? Potresti elaborare? –

+0

Stai creando (e chiedendo) le ombre di denominazione in una classe locale anonima (stai anche sottoclassi di 'Runnable'). Scegli il nome che vuoi scoprire e stampalo prendendo la classe. –

risposta

3

il tuo metodo run() è in una sottoclasse anonima di Runnable dove è anche una classe interna di Tracker.

effettivamente la stessa

package test; 

public class Tracker extends test.parent.Tracker { 

... 
@Override 
    public void track(final Event event) { 
    //anonymous class translated into local class 
    class TrackerRunnable implements Runnable { 
     public void run(){ 
     Tracker.super.track(event); //this works!! why?? 
     super.track(event); // compile error: cannot resolve 
     test.parent.Tracker.track(event); //compile error: can only reference static method 
     } 
    } 

    Executor.execute(new TrackerRunnable()); 
    } 
} 

In Java una classe interna ha anche un riferimento alla classe esterna che "appartiene" a. Si fa riferimento a this per this all'interno di esecuzione, ma se è necessario accedere all'istanza di a cui è associato lo TrackerRunnable, l'utente accederà come Tracker.this. Stessa cosa con Tracker.super. Solo super significa la superclasse di TrackerRunnable non Tracker (in questo caso Runnable).

La cosa più importante da notare è che questa è la sintassi che viene utilizzato per la risoluzione portata solo in classi interne, e che il Tracker qui si riferisce a "l'istanza della classe Tracker di appartenere a". Nel caso di test.parent.Tracker.trackTracker si riferisce alla "classe Tracker", quindi non è possibile chiamare membri di istanza sulla classe stessa.

+1

'Interno non statico' è una tautologia, – EJP

+0

Il mio male sulla terminologia di "static nested class" vs. "inner class". Risposta fissa –

+0

@Pshemo Ciò che EJP significa è ciò che ha detto, ed è indicato nel JLS. Non cito fonti non normative. – EJP