interface enhancements java 8 java functional interface
Questo tutorial spiega le aggiunte all'interfaccia in Java 8 e le differenze tra i concetti Java come una classe astratta, la parola chiave extends, ecc. Con le interfacce:
Abbiamo esplorato tutto Interfacce in Java nel nostro ultimo tutorial. Abbiamo introdotto e trattato i concetti di base delle interfacce in Java, comprese le interfacce multiple.
Prima di Java 8, le interfacce potevano avere solo metodi astratti e variabili statiche e finali. I metodi astratti sono pubblici per impostazione predefinita e devono essere sovrascritti dalla classe che implementa un'interfaccia.
Quindi l'interfaccia era principalmente un contratto ed era coinvolta solo con costanti (statiche e finali) e metodi astratti.
=> Dai un'occhiata alla guida per principianti di Java qui.
Cosa imparerai:
- Modifiche alle interfacce in Java 8
- Interfacce funzionali Java 8
- Interfaccia di classe Vs in Java
- Java estende contro gli attrezzi
- Interfaccia vs classe astratta in Java
- Conclusione
Modifiche alle interfacce in Java 8
La versione Java 8 introduce o ci consente di avere metodi statici e predefiniti nelle interfacce. Utilizzando metodi predefiniti in un'interfaccia, gli sviluppatori possono aggiungere più metodi alle interfacce. In questo modo non disturbano né cambiano le classi che implementano l'interfaccia.
Java 8 consente inoltre all'interfaccia di avere un metodo statico. I metodi statici sono gli stessi che definiamo nelle classi. Notare che il metodo statico non può essere sovrascritto dalla classe che implementa l'interfaccia.
L'introduzione di metodi statici e predefiniti nell'interfaccia ha reso più semplice modificare le interfacce senza problemi e ha anche reso le interfacce più facili da implementare.
Java 8 introduce anche 'Lambda Expressions' all'interno delle interfacce funzionali. Inoltre, da Java 8 in poi ci sono più interfacce funzionali integrate in Java.
In questo tutorial, discuteremo tutte queste aggiunte alle interfacce in Java 8 e discuteremo anche alcune delle differenze tra vari concetti Java come classi astratte, parole chiave extends, ecc. Con le interfacce.
Metodo statico nell'interfaccia in Java
Le interfacce possono anche avere metodi che possono avere definizioni. Questi sono i metodi statici nell'interfaccia. I metodi statici sono definiti all'interno dell'interfaccia e non possono essere sovrascritti o modificati dalle classi che implementano questa interfaccia.
Possiamo chiamare questi metodi statici utilizzando direttamente il nome dell'interfaccia.
L'esempio seguente mostra l'utilizzo del metodo statico.
//interface declaration interface TestInterface { // static method definition static void static_print() { System.out.println('TestInterface::static_print ()'); } // abstract method declaration void nonStaticMethod(String str); } // Interface implementation class TestClass implements TestInterface { // Override interface method @Override public void nonStaticMethod(String str) { System.out.println(str); } } public class Main{ public static void main(String() args) { TestClass classDemo = new TestClass(); // Call static method from interface TestInterface.static_print(); // Call overridden method using class object classDemo.nonStaticMethod('TestClass::nonStaticMethod ()'); } }
Produzione:
Il programma sopra ha una TestInterface. Ha un metodo statico denominato 'static_print' e anche un metodo non statico denominato nonstaticmethod.
Abbiamo implementato TestInterface in TestClass e nonStaticMethod sostituito. Quindi, nel metodo principale, chiamiamo il metodo static_print direttamente utilizzando TestInterface e nonStaticMethod utilizzando l'oggetto di TestClass.
Metodo predefinito dell'interfaccia
Come già accennato, le interfacce precedenti a Java 8 consentivano solo metodi astratti. Quindi forniremo l'implementazione di questo metodo in una classe separata. Se dovessimo aggiungere un nuovo metodo all'interfaccia, dobbiamo fornire il suo codice di implementazione nella stessa classe.
Quindi, se alterassimo l'interfaccia aggiungendovi un metodo, cambierebbe anche la classe di implementazione.
Questa limitazione è stata superata dalla versione Java 8 che consentiva alle interfacce di avere metodi predefiniti. I metodi predefiniti in un certo senso forniscono compatibilità con le versioni precedenti delle interfacce esistenti e non è necessario modificare la classe di implementazione. I metodi predefiniti sono noti anche come 'metodo di estensione virtuale' o 'metodi di difesa'.
I metodi predefiniti vengono dichiarati utilizzando la parola chiave 'default' nella dichiarazione. La dichiarazione è seguita dalla definizione del metodo. Possiamo sovrascrivere il metodo predefinito poiché è disponibile per la classe che implementa l'interfaccia.
Allo stesso modo, possiamo invocarlo utilizzando l'oggetto della classe di implementazione direttamente dall'interfaccia senza sovrascriverlo.
interface TestInterface { // abstract method public void cubeNumber(int num); // default method default void print() { System.out.println('TestInterface :: Default method'); } } class TestClass implements TestInterface { // override cubeNumber method public void cubeNumber(int num) { System.out.println('Cube of given number ' + num+ ':' + num*num*num); } } class Main{ public static void main(String args()) { TestClass obj = new TestClass(); obj.cubeNumber(5); // call default method print using class object obj.print(); } }
Produzione:
domande e risposte del colloquio dell'analista di affari ppt
Il programma Java di cui sopra mostra il metodo predefinito nell'interfaccia. Nel metodo principale, nota che possiamo chiamare il metodo predefinito dell'interfaccia usando l'oggetto classe. Questo perché quando la classe implementa l'interfaccia, il metodo predefinito è disponibile anche per la classe.
Nota: Avremmo potuto sovrascrivere il metodo print () anche nella classe di implementazione. Nota che, se sovrascritto, il modificatore di accesso del metodo predefinito cambierà in pubblico nella classe di implementazione.
Metodi predefiniti ed ereditarietà multipla
Potrebbe verificarsi una situazione in caso di più interfacce in cui ciascuna interfaccia potrebbe avere un metodo predefinito con lo stesso prototipo. In tal caso, il compilatore non sa quale metodo invocare.
Quando si verifica questa situazione in cui il metodo predefinito ha lo stesso prototipo in tutte le interfacce, la soluzione è sovrascrivere il metodo nella classe di implementazione in modo che quando l'oggetto della classe di implementazione chiama il metodo predefinito, il compilatore richiama il metodo implementato nella classe .
Il seguente programma Java dimostra l'utilizzo del metodo predefinito con più interfacce.
//Interface_One interface Interface_One{ //defaultMethod default void defaultMethod(){ System.out.println('Interface_One::defaultMethod'); } } //Interface_Two interface Interface_Two{ //defaultMethod default void defaultMethod(){ System.out.println('Interface_Two::defaultMethod'); } } class TestExample implements Interface_One, Interface_Two{ public void disp(String str){ System.out.println('String is: '+str); } //override defaultMethod to take care of the ambiguity public void defaultMethod(){ System.out.println('TestExample::defaultMethod'); } } class Main{ public static void main(String() args) { TestExample obj = new TestExample(); //call the default method obj.defaultMethod(); } }
Produzione:
Nel programma sopra, abbiamo sovrascritto il metodo predefinito (che ha lo stesso prototipo in entrambe le interfacce) nella classe di implementazione. In questo modo, quando chiamiamo il metodo predefinito dal metodo principale utilizzando l'oggetto della classe di implementazione, viene richiamato il metodo sovrascritto.
il gateway predefinito non è disponibile correzione
Interfacce funzionali Java 8
Un'interfaccia funzionale è un'interfaccia che ha un solo metodo astratto. Può contenere un numero qualsiasi di metodi predefiniti e statici, ma il metodo astratto che contiene è esattamente uno. Inoltre, un'interfaccia funzionale può avere dichiarazioni di metodi di classi di oggetti.
L'interfaccia funzionale è nota come ' Interfaccia del metodo astratto singolo ' o ' Interfaccia SAM '. L'interfaccia SAM è una nuova funzionalità in Java.
In un programma Java, la presenza di un'interfaccia funzionale è indicata utilizzando un file @FunctionalInterface annotazione. Quando il compilatore incontra questa annotazione, allora sa che l'interfaccia che segue questa annotazione è funzionante. Quindi se contiene più di un metodo astratto, allora lampeggia un errore.
L'annotazione @FunctionalInterface tuttavia, non è obbligatorio in Java.
Il seguente programma mostra l'interfaccia funzionale in Java:
//declare a functional interface @FunctionalInterface //annotation indicates it’s a functional interface interface function_Interface{ void disp_msg(String msg); // abstract method // Object class methods. int hashCode(); String toString(); boolean equals(Object obj); } //implementation of Functional Interface class FunctionalInterfaceExample implements function_Interface{ public void disp_msg(String msg){ System.out.println(msg); } } class Main{ public static void main(String() args) { //create object of implementation class and call method FunctionalInterfaceExample finte = new FunctionalInterfaceExample(); finte.disp_msg('Hello, World!!!'); } }
Produzione:
L'interfaccia funzionale nel programma sopra ha un singolo metodo astratto e ha anche una dichiarazione del metodo della classe di oggetti come hashCode, toString ed equals. Nella classe che implementa questa interfaccia, il metodo astratto viene sovrascritto. Nel metodo principale, creiamo un oggetto della classe di implementazione e utilizziamo il metodo.
Interfacce come Runnable e Comparable sono esempi di interfacce funzionali fornite in Java. Java 8 ci consente di assegnare espressioni lambda all'oggetto dell'interfaccia funzionale.
Il seguente programma di esempio lo dimostra.
class Main{ public static void main(String args()) { // use lambda expression to create the object new Thread(()-> {System.out.println('New thread created with functional interface');}).start(); } }
Produzione:
Java 8 fornisce anche molte interfacce funzionali integrate nel pacchetto java.util.function.
Queste interfacce integrate sono descritte di seguito:
# 1) Predicato
Questa è un'interfaccia funzionale in Java che ha un unico metodo di prova astratto. Il metodo 'test' restituisce il valore booleano dopo aver verificato l'argomento specificato.
Di seguito è riportato il prototipo per il metodo di test dell'interfaccia Predicate.
public interface Predicate { public boolean test(T t); }
# 2) BinaryOperator
L'interfaccia BinaryOperator fornisce un metodo astratto 'apply' che accetta due argomenti e restituisce un valore risultante dello stesso tipo degli argomenti.
Il prototipo del metodo di accettazione è:
public interface BinaryOperator { public T apply (T x, T y); }
# 3) Funzione
L'interfaccia Function è un'interfaccia funzionale che dispone anche di un metodo astratto denominato 'apply'. Questo metodo apply, tuttavia, accetta un singolo argomento di tipo T e restituisce un valore di tipo R.
Il prototipo del metodo di applicazione è il seguente:
public interface Function { public R apply(T t); }
Il seguente programma Java mostra il predicato dell'interfaccia funzionale incorporato sopra.
import java.util.*; import java.util.function.Predicate; class Main { public static void main(String args()) { // create a list of strings List names = Arrays.asList('Karen','Mia','Sydney','Lacey','Megan'); // declare string type predicate and use lambda expression to create object Predicate p = (s)->s.startsWith('M'); System.out.println('Names starting with M:'); // Iterate through the list for (String st:names) { // test each entry with predicate if (p.test(st)) System.out.println(st); } } }
Produzione:
Come possiamo vedere nel programma sopra abbiamo un elenco di stringhe. Utilizzando l'interfaccia funzionale Predicate, testiamo se l'elemento nella stringa inizia con M e, in caso affermativo, stampa il nome.
Interfaccia di classe Vs in Java
Sebbene la classe e l'interfaccia siano simili in quanto hanno una sintassi simile, queste due entità hanno più differenze che somiglianze.
Elenchiamo alcune delle differenze tra classe e interfaccia in Java.
Classe | Interfaccia |
---|---|
Possiamo istanziare e creare oggetti da una classe. | Non è possibile creare un'istanza di un'interfaccia. |
La parola chiave 'classe' viene utilizzata per creare una classe. | L'interfaccia viene creata utilizzando la parola chiave 'interfaccia'. |
Le classi non supportano l'ereditarietà multipla in Java. | Le interfacce supportano l'ereditarietà multipla in Java. |
La classe contiene i costruttori. | Le interfacce non contengono costruttori. |
La classe non può contenere metodi astratti. | Le interfacce contengono solo metodi astratti. |
La classe può avere variabili e metodi predefiniti, pubblici, privati o protetti. | L'interfaccia ha solo variabili e metodi pubblici per impostazione predefinita. |
Non è obbligatorio associare modificatori di non accesso alle variabili della classe. | Le interfacce possono avere variabili statiche o finali. |
Possiamo ereditare un'altra classe da una classe. | Non possiamo ereditare una classe dall'interfaccia. |
La classe può essere ereditata utilizzando la parola chiave 'extends'. | L'interfaccia può essere implementata da un'altra classe utilizzando la parola chiave 'implements'. Può essere ereditato da un'altra interfaccia utilizzando la parola chiave 'extends'. |
Java estende contro gli attrezzi
'Si estende' | 'Attrezzi' |
---|---|
Le interfacce supportano solo modificatori statici e finali non di accesso. | Abstract supporta tutti i modificatori di non accesso come statico, finale, non statico e non finale. |
Una classe utilizza la parola chiave 'extends' per ereditare da un'altra classe. | La parola chiave 'implements' viene utilizzata da una classe per implementare un'interfaccia. |
Una classe che eredita un'altra classe può o non può sovrascrivere tutti i metodi della classe genitore. | La classe che implementa l'interfaccia deve sovrascrivere tutti i metodi astratti dell'interfaccia. |
Possiamo estendere solo una classe alla volta usando la parola chiave extends. | Possiamo implementare più interfacce utilizzando la parola chiave 'implements'. |
Un'interfaccia può estendere un'altra interfaccia utilizzando la parola chiave 'extends'. | Un'interfaccia non può implementare un'altra interfaccia utilizzando le parole chiave 'implementa'. |
Può l'interfaccia astratta dell'attrezzo di classe in Java
Sì, una classe astratta può implementare un'interfaccia utilizzando la parola chiave 'implements'. La classe abstract non ha bisogno di implementare tutti i metodi astratti dell'interfaccia. Ma nel complesso è una buona pratica di progettazione avere un'interfaccia con tutti i metodi astratti, quindi una classe astratta che implementa questa interfaccia e quindi le classi concrete.
Di seguito è riportato un esempio di tale implementazione in Java.
Qui java.util.List è un'interfaccia. Questa interfaccia è implementata da java.util.AbstractList. Quindi questa classe AbstractList viene estesa da due classi concrete, ovvero LinkedList e ArrayList.
Se le classi LinkedList e ArrayList avessero implementato direttamente l'interfaccia List, allora avrebbero dovuto implementare tutti i metodi astratti dell'interfaccia List.
Ma in questo caso, la classe AbstractList implementa i metodi dell'interfaccia List e li passa a LinkedList e ArrayList. Quindi qui otteniamo il vantaggio di dichiarare il tipo dall'interfaccia e la flessibilità della classe astratta di implementare il comportamento comune.
Quando utilizzare la classe astratta e l'interfaccia in Java
Utilizziamo principalmente una classe astratta per definire un comportamento predefinito o comune delle classi figlie che si estenderanno da questa classe astratta. Un'interfaccia viene utilizzata per definire un contratto tra due sistemi che interagiscono in un'applicazione.
Alcune situazioni specifiche sono ideali per le interfacce da utilizzare e alcuni problemi che possono essere risolti solo utilizzando classi astratte. In questa sezione, discuteremo di quando possiamo usare l'interfaccia e quando possiamo usare le classi astratte.
Quando utilizzare un'interfaccia:
- Le interfacce vengono utilizzate principalmente quando abbiamo una piccola funzionalità concisa da implementare.
- Quando implementiamo le API e sappiamo che non cambieranno per un po ', quella volta andremo per le interfacce.
- Le interfacce ci consentono di implementare l'ereditarietà multipla. Quindi, quando abbiamo bisogno di implementare l'ereditarietà multipla nella nostra applicazione, andiamo per le interfacce.
- Quando abbiamo una vasta gamma di oggetti, ancora una volta le interfacce sono una scelta migliore.
- Anche quando dobbiamo fornire una funzionalità comune a molte classi non correlate, vengono comunque utilizzate le interfacce.
Quando utilizzare una classe astratta:
- Le classi astratte vengono utilizzate principalmente quando è necessario utilizzare l'ereditarietà nella nostra applicazione.
- Poiché le interfacce si occupano di metodi e variabili pubblici, ogni volta che vogliamo utilizzare modificatori di accesso non pubblico nel nostro programma, utilizziamo classi astratte.
- Se è necessario aggiungere nuovi metodi, è meglio farlo in una classe astratta che nell'interfaccia. Perché se aggiungiamo un nuovo metodo nell'interfaccia, l'intera implementazione cambia poiché le interfacce hanno solo prototipi di metodo e l'implementazione della classe che utilizza l'interfaccia fornirà l'implementazione.
- Se vogliamo che siano sviluppate versioni differenti dei componenti, allora optiamo per la classe astratta. Possiamo cambiare le classi astratte più facilmente. Ma le interfacce non possono essere modificate. Se vogliamo una nuova versione, dobbiamo riscrivere l'intera interfaccia.
- Quando vogliamo fornire un'implementazione comune per tutti i componenti, la classe astratta è la scelta migliore.
Interfaccia vs classe astratta in Java
Di seguito sono riportate alcune delle differenze tra le interfacce e le classi astratte in Java.
Interfaccia | Classe astratta |
---|---|
Un'interfaccia viene dichiarata utilizzando la parola chiave 'interfaccia'. | Una classe astratta viene dichiarata utilizzando la parola chiave 'abstract'. |
L'interfaccia può essere implementata utilizzando la parola chiave 'implements'. | L'abstract può essere ereditato utilizzando la parola chiave 'extends'. |
Un'interfaccia non può estendere una classe o implementare un'interfaccia, può solo estendere un'altra interfaccia. | Una classe astratta può estendere una classe o implementare più interfacce. |
I membri dell'interfaccia possono essere solo pubblici. | I membri della classe astratta possono essere pubblici, privati o protetti. |
Non è possibile utilizzare un'interfaccia per fornire un'implementazione. Può essere utilizzato solo come dichiarazione. | Una classe astratta può essere utilizzata per implementare l'interfaccia. |
L'ereditarietà multipla può essere ottenuta utilizzando le interfacce. | La classe astratta non supporta l'ereditarietà multipla. |
Le interfacce possono avere solo metodi astratti. Da Java 8, può avere metodi statici e predefiniti. | Una classe astratta può avere un metodo astratto o non astratto. |
Enum Ereditarietà in Java
Abbiamo discusso i tipi di dati enum nella nostra discussione sui tipi di dati in Java. Tutte le enumerazioni si estendono dalla classe java.lang.Enum. Questa classe java.lang.Enum è una classe astratta.
Inoltre, tutte le classi enum in Java sono 'finali' per impostazione predefinita. Quindi, un tentativo di ereditare una classe da qualsiasi classe enum si traduce in un errore del compilatore.
Poiché Java non consente l'ereditarietà multipla, non possiamo ereditare la classe enum da qualsiasi altra classe poiché la classe enum eredita già da java.lang.Enum. Tuttavia, le classi enum possono implementare interfacce in Java e questo è chiamato ereditarietà Enum in Java.
Di seguito è riportato un esempio di Enum Inheritance in Java.
//WeekDays interface declaration interface WeekDays { public void displaydays(); } //enum class implementing WeekDays interface enum Days implements WeekDays { SUNDAY, MONDAY, TUESDAY, WEDNESDAY, THURSDAY,FRIDAY, SATURDAY; public void displaydays() { //Override displaydays method System.out.println('The day of the week: ' + this); } } class Main { public static void main(String() args) { Days.MONDAY.displaydays(); //access enum value } }
Produzione:
Qui abbiamo un'interfaccia WeekDays con un prototipo di metodo astratto displaydays (). Quindi definiamo una classe enum Days che implementa l'interfaccia WeekDays. Qui definiamo i valori enum da SUNDAY a SATURDAY e sovrascriviamo anche il metodo displaydays.
Infine, nel metodo main, accediamo al valore enum e lo visualizziamo.
Domande frequenti
D # 1) Cosa succede se fornisci un corpo del metodo nell'interfaccia?
Risposta: Per le versioni di Java precedenti a Java 8, il corpo del metodo non è consentito nell'interfaccia. Ma a partire da Java 8, possiamo definire metodi predefiniti o statici all'interno dell'interfaccia.
D # 2) Un'interfaccia può avere variabili in Java 8?
Risposta: Possiamo avere variabili costanti in Java 8 usando modificatori statici e finali. Ma non possiamo avere variabili di istanza nelle interfacce Java. Qualsiasi tentativo di dichiarare le variabili di istanza in un'interfaccia risulterà in un errore del compilatore.
D # 3) Quali sono i miglioramenti nelle interfacce in Java 8?
Risposta: Il miglioramento più importante per le interfacce in Java 8 è che i metodi statici e predefiniti sono consentiti nelle interfacce. Possiamo avere metodi dichiarati come statici o predefiniti e definirli all'interno dell'interfaccia.
D # 4) Possiamo sovrascrivere il metodo predefinito nell'interfaccia Java?
Risposta: No. Non è obbligatorio sovrascrivere il metodo predefinito nell'interfaccia. Questo perché quando implementiamo un'interfaccia in una classe, il metodo predefinito della classe è accessibile alla classe di implementazione. Quindi utilizzando l'oggetto della classe di implementazione, possiamo accedere al metodo predefinito dell'interfaccia.
D # 5) Le interfacce possono avere campi in Java?
domande di intervista sui servizi web riposanti java
Risposta: Sì, possiamo avere campi o variabili nelle interfacce in Java ma per impostazione predefinita, tutti questi campi sono statici, finali e pubblici.
Conclusione
In questo tutorial, abbiamo discusso le modifiche apportate alle interfacce in Java 8. Java 8 ha introdotto metodi statici e predefiniti nelle interfacce. In precedenza potevamo avere solo metodi astratti nell'interfaccia. Ma da Java 8 in poi, possiamo definire metodi predefiniti e statici in Java.
Inoltre, Java 8 consente l'uso di espressioni lambda con le interfacce funzionali in Java. Quindi abbiamo discusso anche di classi e interfacce astratte e abbiamo visto quando usarle in Java. Abbiamo anche visto l'ereditarietà enum in Java.
Abbiamo anche discusso alcune delle differenze tra estensioni e implementazioni, classe e interfaccia, classe astratta e interfaccia, ecc.
=> Controlla TUTTI i tutorial Java qui.
Lettura consigliata
- Tutorial sull'interfaccia Java e sulla classe astratta con esempi
- Interfacce comparabili e di confronto in Java
- Interfaccia ListIterator in Java con esempi
- Set Interface In Java: Java Set Tutorial with examples
- Marker Interface in Java: serializzabile e clonabile
- Metodo Java String length () con esempi
- Distribuzione Java: creazione ed esecuzione di file JAR Java
- Come utilizzare il metodo Java toString?