JavaRush /Java блогы /Random-KK /Java тіліндегі интерфейстер

Java тіліндегі интерфейстер

Топта жарияланған
Сәлеметсіз бе! Бүгін біз Java тіліндегі маңызды ұғым - интерфейстер туралы сөйлесетін боламыз. Бұл сөз сізге таныс шығар. Мысалы, көптеген компьютерлік бағдарламалар мен ойындардың интерфейстері бар. Кең мағынада интерфейс бір-бірімен өзара әрекеттесетін екі тарапты байланыстыратын «қашықтан басқару пульті» түрі болып табылады. Күнделікті өмірдегі интерфейстің қарапайым мысалы - теледидардың қашықтан басқару құралы. Ол екі нысанды, адам мен теледидарды қосады және әртүрлі тапсырмаларды орындайды: дыбыс деңгейін жоғарылату немесе азайту, арналарды өзгерту, теледидарды қосу немесе өшіру. Бір тарапқа (адам) әрекетті орындау үшін екінші тарап интерфейске қол жеткізуі керек (қашықтан басқару түймесін басыңыз). Мысалы, теледидар арнаны келесіге ауыстыру үшін. Бұл жағдайда пайдаланушыға теледидардың құрылғысын және оның ішінде арнаны өзгерту процесі қалай жүзеге асырылатынын білудің қажеті жоқ. Java тілінде интерфейстер не үшін қажет - 1Пайдаланушы қол жеткізе алатын барлық нәрсе интерфейс болып табылады . Негізгі міндет - қажетті нәтижеге қол жеткізу. Мұның бағдарламалауға және Java-ға қандай қатысы бар? Тікелей :) Интерфейс құру кәдімгі класс құруға өте ұқсас, бірақ сөздің орнына classсөзді көрсетеміз interface. Ең қарапайым Java интерфейсін қарастырайық және оның қалай жұмыс істейтінін және не үшін қажет екенін анықтайық:
public interface Swimmable  {

     public void swim();
}
Біз жүзе алатынSwimmable интерфейсті жасадық . Бұл бір «түйме» бар біздің қашықтан басқару пульті сияқты нәрсе: әдіс «жүзу». Бұл « қашықтан басқару пультін » қалай пайдалана аламыз ? Осы мақсатта әдіс, яғни. қашықтан басқару құралындағы түймені іске қосу керек. Интерфейсті пайдалану үшін оның әдістерін бағдарламамыздың кейбір кластары жүзеге асыруы керек. Нысандары «жүзе алады» сипаттамасына сәйкес келетін сыныпты ойлап көрейік. Мысалы, үйрек класы қолайлы : swim()Duck
public class Duck implements Swimmable {

    public void swim() {
        System.out.println("Duck, swim!");
    }

    public static void main(String[] args) {

        Duck duck = new Duck();
        duck.swim();
    }
}
Мұнда не көріп тұрмыз? Класс кілт сөзді қолданатын Duckинтерфейспен байланысты . Естеріңізде болса, біз мұрагерлікте екі классты қосу үшін ұқсас механизмді қолдандық, тек « кеңейтеді » сөзі бар еді. Түсінікті болу үшін “ ” сөзін сөзбе-сөз аударуға болады: “қоғамдық класс интерфейсті жүзеге асырады .” Бұл интерфейспен байланысты класс оның барлық әдістерін жүзеге асыруы керек дегенді білдіреді. Назар аударыңыз: біздің сыныпта интерфейстегі сияқты әдіс бар және оның ішінде логика бар. Бұл міндетті талап. Егер біз жай ғана “ ” деп жазып , сыныпта әдісті жасамасақ , компилятор бізге қате жіберер еді: Duck дерексіз емес және Swimmable ішіндегі swim() дерексіз әдісін жоққа шығармайды Неліктен бұл орын алады? Егер қатені теледидардың мысалы арқылы түсіндірсек, біз адамға арналарды қалай өзгерту керектігін білмейтін теледидардан «арнаны өзгерту» түймесі бар қашықтан басқару құралын беретініміз белгілі болды. Осы кезде түймені қалағаныңызша басыңыз, ештеңе жұмыс істемейді. Қашықтан басқару пульті арналарды өзгертпейді: ол тек теледидарға сигнал береді, оның ішінде арнаны өзгертудің күрделі процесі жүзеге асырылады. Біздің үйрекпен де солай: интерфейс арқылы оған қол жеткізу үшін ол жүзе алуы керек . Егер ол мұны қалай істеу керектігін білмесе, интерфейс екі жақты - адам мен бағдарламаны байланыстырмайды. Адам бағдарламаның ішіндегі нысанды қалқымалы ету әдісін пайдалана алмайды . Енді сіз интерфейстердің не үшін екенін анық көрдіңіз. Интерфейс осы интерфейсті жүзеге асыратын сыныптар болуы керек әрекетті сипаттайды. «Мінез-құлық» - әдістер жиынтығы. Егер біз бірнеше мессенджер жасағымыз келсе, мұны істеудің ең оңай жолы - интерфейс жасау . Кез келген мессенджер не істей алуы керек? Жеңілдетілген пішінде хабарларды қабылдау және жіберу. Swimmableimplementspublic class Duck implements SwimmableDuckSwimmableDuckSwimmableswim()public class Duck implements Swimmableswim()DuckSwimmableSwimmableswim()DuckMessenger
public interface Messenger{

     public void sendMessage();

     public void getMessage();
}
Енді біз осы интерфейсті енгізу арқылы жай ғана хабаршы сыныптарымызды жасай аламыз. Компилятордың өзі бізді оларды сыныптарда енгізуге «мәжбүрлейді». Telegram:
public class Telegram implements Messenger {

    public void sendMessage() {

        System.out.println("Sending a message to Telegram!");
    }

     public void getMessage() {
         System.out.println("Reading the message in Telegram!");
     }
}
WhatsApp:
public class WhatsApp implements Messenger {

    public void sendMessage() {

        System.out.println("Sending a WhatsApp message!");
    }

     public void getMessage() {
         System.out.println("Reading a WhatsApp message!");
     }
}
Viber:
public class Viber implements Messenger {

    public void sendMessage() {

        System.out.println("Sending a message to Viber!");
    }

     public void getMessage() {
         System.out.println("Reading a message in Viber!");
     }
}
Бұл қандай артықшылықтар береді? Олардың ең маңыздысы - бос муфта. Біз тұтынушы деректерін жинайтын бағдарламаны әзірлеп жатырмыз деп елестетіңіз. Класта Clientклиент қай хабаршыны пайдаланатынын көрсететін өріс болуы керек. Интерфейстерсіз ол біртүрлі көрінеді:
public class Client {

    private WhatsApp whatsApp;
    private Telegram telegram;
    private Viber viber;
}
Біз үш өріс жасадық, бірақ клиентте бір ғана хабаршы оңай болуы мүмкін. Тек қайсысы екенін білмейміз. Клиентпен байланыссыз қалмау үшін барлық мүмкін нұсқаларды сыныпқа «итеру» керек. Олардың біреуі немесе екеуі әрқашан сонда болады nullжәне бағдарламаның жұмыс істеуі үшін олар мүлдем қажет емес. Оның орнына біздің интерфейсті қолданған дұрыс:
public class Client {

    private Messenger messenger;
}
Бұл «бос муфтаның» мысалы! Сыныпта белгілі бір мессенджер сыныбын көрсетудің орнына Clientбіз клиентте хабаршы бар екенін айтамыз. Қайсысы бағдарлама барысында анықталады. Бірақ бұл үшін интерфейстер не үшін қажет? Неліктен олар тілге қосылды? Сұрақ жақсы және дұрыс! Дәл осындай нәтижеге кәдімгі мұра арқылы қол жеткізуге болады, солай ма? Сынып Messengerата-ана класы, және Viber, Telegramжәне WhatsAppмұрагерлері болып табылады. Шынында да, мұны істеуге болады. Бірақ бір қулық бар. Өздеріңіз білетіндей, Java-да көп мұра жоқ. Бірақ интерфейстердің бірнеше іске асырылуы бар. Класс өзі қалағандай көптеген интерфейстерді жүзеге асыра алады. SmartphoneБізде өрісі бар сынып бар деп елестетіп көріңіз Application- смартфонда орнатылған қолданба.
public class Smartphone {

    private Application application;
}
Қолданба мен мессенджер, әрине, ұқсас, бірақ бәрібір олар әртүрлі нәрселер. Messenger мобильді және жұмыс үстелі болуы мүмкін, ал Application мобильді қосымша болып табылады. TelegramСонымен, егер мұраны пайдалансақ, сыныпқа нысанды қоса алмас едік Smartphone. Ақыр соңында, класс мұраға Telegramие бола алмайды . Біз қазірдің өзінде оны мұраға алып , оны осы пішінде сыныпқа қоса алдық . Бірақ сынып екі интерфейсті де оңай жүзеге асыра алады! Сондықтан сыныпта an objectіні ретінде , ал сыныпта ретінде іске асыра аламыз . Бұл қалай орындалды: ApplicationMessengerMessengerClientTelegramClientTelegramMessengerSmartphoneApplication
public class Telegram implements Application, Messenger {

    //...methods
}

public class Client {

    private Messenger messenger;

    public Client() {
        this.messenger = new Telegram();
    }
}


public class Smartphone {

    private Application application;

    public Smartphone() {
        this.application = new Telegram();
    }
}
Енді біз сыныпты Telegramөз қалауымызша пайдалана аламыз. Бір жерде ол рөлде Application, бір жерде рөлде ойнайды Messenger. Сіз интерфейстердегі әдістер әрқашан «бос» екенін байқаған боларсыз, яғни олардың іске асырылуы жоқ. Мұның себебі қарапайым: интерфейс әрекетті сипаттайды, оны жүзеге асырмайды. «Интерфейсті жүзеге асыратын сыныптардың барлық an objectілері Swimmableқалқымалы болуы керек»: интерфейс бізге осыны айтады. Балық, үйрек немесе жылқы қалай жүзетіні туралы сұрақ интерфейс үшін емес, және Fishсыныптар Duckүшін бар. HorseАрнаны өзгерту теледидардың міндеті сияқты. Қашықтан басқару құралы сізге мұны істеу үшін жай ғана түймені береді. Дегенмен, Java8-де қызықты қосымша бар - әдепкі әдістер. Мысалы, сіздің интерфейсіңізде 10 әдіс бар. Олардың 9-ы әртүрлі сыныптарда әртүрлі жүзеге асырылады, бірақ біреуі барлығына бірдей жүзеге асырылады. Бұрын Java8 шығарылғанға дейін интерфейстердің ішіндегі әдістер мүлде іске асырылмады: компилятор бірден қате жіберді. Енді сіз мұны келесідей жасай аласыз:
public interface Swimmable {

   public default void swim() {
       System.out.println("Swim!");
   }

   public void eat();

   public void run();
}
Түйінді сөзді пайдаланып defaultинтерфейсте әдепкі іске асыру әдісін жасадық. Бізге басқа екі әдісті eat()және , run()іске асыратын барлық сыныптарда өзіміз енгізу керек болады Swimmable. Мұны әдіспен жасаудың қажеті жоқ swim(): іске асыру барлық сыныптарда бірдей болады. Айтпақшы, сіз өткен тапсырмаларда интерфейстерді бірнеше рет кездестірдіңіз, бірақ оны өзіңіз байқамағансыз :) Міне, айқын мысал: Неліктен бізге Java тіліндегі интерфейстер керек - 2Сіз интерфейстермен Listжәне Set! Дәлірек айтқанда, олардың жүзеге асуларымен - ArrayList, LinkedList, HashSetжәне т.б. Дәл сол диаграммада бір сынып бірден бірнеше интерфейсті орындайтын мысал көрсетілген. Мысалы, LinkedListол интерфейстерді Listжәне Deque(екі жақты кезек) жүзеге асырады. Сіз сондай-ақ интерфейспен Map, дәлірек айтсақ, оның іске асырылуымен таныссыз - HashMap. Айтпақшы, бұл диаграммада сіз бір мүмкіндікті көре аласыз: интерфейстер бір-бірінен мұралануы мүмкін. Интерфейс SortedMapкелесіден мұраланған Mapжәне Dequeкезектен мұраланған Queue. Бұл интерфейстер арасындағы байланысты көрсеткіңіз келсе, бірақ бір интерфейс екіншісінің кеңейтілген нұсқасы болса қажет. Интерфейсі бар мысалды қарастырайық Queue- кезек. Біз әлі жинақтарды аралап көрген жоқпыз Queue, бірақ олар өте қарапайым және дүкендегі кәдімгі желі сияқты реттелген. Элементтерді тек кезектің соңына қосып, оларды тек басынан ғана алып тастай аласыз. Белгілі бір кезеңде әзірлеушілер екі жағынан элементтерді қосу және қабылдау үшін кезектің кеңейтілген нұсқасын қажет етті. Интерфейс осылай құрылды Deque- екі жақты кезек. Ол кәдімгі кезектің барлық әдістерін қамтиды, өйткені ол екі жақты кезектің «ата-анасы» болып табылады, бірақ жаңа әдістер қосылды.
Пікірлер
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION