Abstrakt klass vs. Gränssnitt i Java: Förklaring med exempel

Abstrakta klasser och gränssnitt används för abstraktion i Java. Abstraktion i objektorienterad programmering syftar på att dölja implementeringsdetaljer för slutanvändarna.

I abstraktion kan du veta vilka funktionerna är, men du kan inte veta hur de implementerades.

Låt oss titta på var och en av dem och försöka förstå varför de används.

Abstrakt klass

En klass som inte kan instansieras som ett objekt och kan ha eller inte har abstrakta metoder i sig kallas en abstrakt klass i Java. En abstrakt metod är en metod som inte har ett genomförandeorgan när den deklareras.

Exempel på en abstrakt klass GraphicObject – Oracle

Du kan skapa en abstrakt klass genom att ange det abstrakta nyckelordet före klassnyckelordet.

abstract class abstractClass {
    void run() {
        System.out.println("ran");
    }
}

En abstrakt klass kan utökas med andra klasser. Med andra ord kan den också underklassas.

abstract class AbstractClass {
    void run() {
        System.out.println("ran");
    }
}

class ExtendingAbstractClass extends AbstractClass {
    void newMethod() {
        System.out.println("new");
    }

    @Override
    void run() {
        System.out.println("override");
    }
}

Abstrakta klasser används för att implementera vanliga metoder bland flera klasser som utökar en given abstrakt klass. Möjligheten att definiera abstrakta metoder i abstrakta klasser gör dem också otroligt användbara för klasser som har liknande metoder men med olika implementeringar. Låt oss ta ett exempel.

Tänk på en bil som har vissa funktioner, som start, stopp, backning etc. Dessa funktioner är vanliga bland alla typer av bilar.

Men hur är det med automationsfunktioner som självkörning? Implementeringen av dessa funktioner kan skilja sig åt för olika typer av bilar. Låt oss se hur du kan skapa ett objektorienterat program relaterat till det.

Först och främst, skapa en bilklass som kommer att utökas med flera klasser av olika biltyper.

abstract class Car {
    void start() {
        // implementation
        System.out.println("runs car");
    }

    void stop() {
        // implementation
        System.out.println("engine stops");
    }

    void reverse() {
        // implementation
        System.out.println("reverse mode enabled");
    }

    abstract void selfDrive();
}

Metoden start(), stop() och reverse() är metoder som är vanliga i alla bilar. Så deras implementering är redan definierad i själva bilklassen. En viss typ av bil kan dock ha olika implementeringar av självkörningsläge. Och därmed kan du definiera selfDrive() som en abstrakt metod och implementera den på olika sätt i olika klasser av olika typer av bilar.

class CarTypeA extends Car {
    @Override
    void start() {
        super.start();
    }

    @Override
    void stop() {
        super.stop();
    }

    @Override
    void reverse() {
        super.reverse();
    }

    void selfDrive() {
        // custom implementation
        System.out.println("Type A self driving mode enabled");
    }
}
class CarTypeB extends Car {
    // ...all similar methods

    void selfDrive() {
        // custom implementation
        // different implementation than CarTypeB
        System.out.println("Type B self driving mode enabled");
    }
}

Det är viktigt att notera att om en underklass inte implementerar alla abstrakta metoder som definieras i den abstrakta klassen, så bör den deklareras som en abstrakt klass i sig.

Gränssnitt

Ett gränssnitt är ett sätt att tala om för en klass vilka metoder som måste implementeras av den. Om du till exempel betraktar exemplet med en bil, har den några grundläggande funktioner. Den kan starta, röra sig och stanna. Dessa funktioner är vanliga i alla bilar.

Så om du implementerar ett gränssnitt för en bil i en klass måste du implementera alla metoder för att bilen ska fungera korrekt och säkert.

I likhet med abstrakta klasser kan vi inte instansiera eller skapa objekt i ett gränssnitt. Den kan betraktas som en helt abstrakt klass eftersom den endast innehåller abstrakta metoder, dvs metoder utan implementeringsorgan.

Du kan skapa ett gränssnitt genom att använda nyckelordet för gränssnittet.

interface CAR {
    void start();
    void stop();
    void move();
}

Implementera ett gränssnitt genom att använda nyckelordet implements när du definierar en klass.

class CarTypeB implements CAR {
    public void start() {
        System.out.println("started");
    }

    public void stop() {
        System.out.println("stopped");
    }

    public void move() {
        System.out.println("running");
    }
}

Likhet

Ingen instansiering som ett objekt är det enda som abstrakta klasser och gränssnitt har gemensamt.

Skillnader

Abstrakt klassgränssnitt Arv och implementering Endast en abstrakt klass kan ärvas av en klass. Flera gränssnitt kan implementeras av en klass. VariabeltyperDen kan ha slutliga, icke-slutliga, statiska och icke-statiska variabler. Den kan endast ha statiska och slutliga variabler. MetodtyperDen kan innehålla både abstrakta och icke-abstrakta metoder.Den kan bara innehålla abstrakta metoder, men statiska metoder är ett undantag.ÅtkomstmodifierareEn abstrakt klass kan ha en åtkomstmodifierare. Metodsignaturerna som definieras i gränssnittet är offentliga som standard. Ett gränssnitt har ingen åtkomstmodifierare. Konstruktörer och destruktorerDet kan deklarera konstruktörer och destruktorer. Det kan inte deklarera konstruktörer eller destruktorer.SpeedFastSlowSkillnader mellan abstrakt klass och gränssnitt

När ska man använda abstrakt klass och gränssnitt?

Använd abstrakta klasser när:

  • Du vill dela några vanliga metoder och fält mellan flera klasser.
  • Deklarerar icke-statiska och icke-slutliga fält för att ändra tillståndet för objektet som de är bundna till.

Du kan använda gränssnitt när:

  • Du vill definiera beteendet för en klass som implementerar gränssnittet, men du bryr dig inte om hur det implementeras.
  • Du vill se till att en klass implementerar alla metoder för att fungera korrekt.

Slutord

Gränssnitt används främst för att skapa API:er eftersom de kan tillhandahålla en struktur för att implementera funktionalitet utan att oroa sig för den faktiska implementeringen.

Abstrakta klasser används vanligtvis för att dela gemensamma abstrakta och icke-abstrakta metoder mellan flera klasser, vilket utökar den abstrakta klassen för att göra koden mer återanvändbar.

Lär dig mer om Java med hjälp av dessa onlinekurser för java. Förbereder du dig för en intervju på Java? Här är några intervjufrågor om objektorienterad programmering.