JavaRush /Java blogi /Random-UZ /Java dasturchisi uchun intervyudan olingan savollar va ja...

Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish. 14-qism

Guruhda nashr etilgan
Feyerverk! Dunyo doimo harakatda va biz doimo harakatdamiz. Ilgari Java dasturchisi bo'lish uchun biroz Java sintaksisini bilish kifoya edi, qolganlari esa kelardi. Vaqt o'tishi bilan Java dasturchisi bo'lish uchun zarur bo'lgan bilim darajasi sezilarli darajada o'sdi, shuningdek, talab qilinadigan bilimlarning pastki satrini yuqoriga ko'tarishda davom etayotgan raqobat ham. Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish.  14-1-qismAgar siz haqiqatan ham dasturchi bo'lishni istasangiz, buni odatiy hol sifatida qabul qilishingiz va siz kabi yangi boshlanuvchilar orasida ajralib turish uchun puxta tayyorgarlik ko'rishingiz kerak. Bugun biz nima qilamiz, aniqrog'i, biz 250 dan ortiq savollarni tahlil qilishni davom ettiramiz . Oldingi maqolalarda biz kichik darajadagi barcha savollarni ko'rib chiqdik va bugun biz o'rta darajadagi savollarni ko'rib chiqamiz. Garchi bu 100% o'rta darajadagi savollar emasligini ta'kidlayman, lekin siz ularning ko'pchiligini kichik darajadagi intervyuda uchratishingiz mumkin, chunki aynan shunday suhbatlarda sizning nazariy bazangiz batafsil o'rganiladi, o'rta o'quvchi uchun esa savollar ko'proq uning tajribasini tekshirishga qaratilgan. Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish.  14-2-qismAmmo, ortiqcha uzatmasdan, keling, boshlaylik.

O'rta

Umumiy

1. Protsessual/funktsional dasturlash bilan solishtirganda OOP ning afzalliklari va kamchiliklari qanday?

Juinior uchun savollarni tahlil qilishda shu savol bor edi va shunga ko'ra men allaqachon javob berdim. Ushbu savol va uning javobini maqolaning ushbu qismida, 16 va 17-savollarda qidiring .

2. Agregatsiya kompozitsiyadan nimasi bilan farq qiladi?

OOPda "Has-A Relationship" umumiy tushunchasi ostida birlashtirilgan ob'ektlar o'rtasidagi o'zaro ta'sirning bir necha turlari mavjud. Bu munosabat bir ob'ekt boshqa ob'ektning tarkibiy qismi ekanligini ko'rsatadi. Shu bilan birga, bu munosabatning ikkita kichik turi mavjud: Kompozitsiya - bir ob'ekt boshqa ob'ektni yaratadi va boshqa ob'ektning ishlash muddati yaratuvchining umriga bog'liq. Agregatsiya - ob'ekt qurilish jarayonida boshqa ob'ektga havola (ko'rsatkich) oladi (bu holda, boshqa ob'ektning ishlash muddati yaratuvchining ishlash muddatiga bog'liq emas). Yaxshiroq tushunish uchun keling, aniq bir misolni ko'rib chiqaylik. Bizda ma'lum bir avtomobil sinfi bor - Avtomobil , u o'z navbatida turdagi ichki maydonlarga ega - Dvigatel va yo'lovchilar ro'yxati - List<Passenger> , shuningdek, harakatni boshlash usuli mavjud - startMoving() :
public class Car {

 private Engine engine;
 private List<Passenger> passengers;

 public Car(final List<Passenger> passengers) {
   this.engine = new Engine();
   this.passengers = passengers;
 }

 public void addPassenger(Passenger passenger) {
   passengers.add(passenger);
 }

 public void removePassengerByIndex(Long index) {
   passengers.remove(index);
 }

 public void startMoving() {
   engine.start();
   System.out.println("Машина начала своё движение");
   for (Passenger passenger : passengers) {
     System.out.println("В машине есть пассажир - " + passenger.getName());
   }
 }
}
Bunday holda, Kompozitsiya Avtomobil va Dvigatel o'rtasidagi bog'liqlikdir , chunki avtomobilning ishlashi to'g'ridan-to'g'ri vosita ob'ektining mavjudligiga bog'liq, chunki dvigatel = null bo'lsa, biz NullPointerException ni olamiz . O'z navbatida, dvigatel mashinasiz mavjud bo'lolmaydi (nega bizga mashinasiz dvigatel kerak?) va bir vaqtning o'zida bir nechta mashinalarga tegishli bo'lishi mumkin emas. Bu shuni anglatadiki, agar biz Avtomobil ob'ektini o'chirsak, Dvigatel ob'ektiga boshqa havolalar bo'lmaydi va u tez orada axlat yig'uvchi tomonidan o'chiriladi . Ko'rib turganingizdek, bu munosabatlar juda qattiq (kuchli). Aggregatsiya - bu Avtomobil va yo'lovchi o'rtasidagi bog'liqlik , chunki Avtomobilning ishlashi hech qanday tarzda Yo'lovchi tipidagi ob'ektlarga va ularning soniga bog'liq emas. Ular avtomobilni tark etishlari mumkin - removePassengerByIndex(Long index) yoki yangilarini kiritishlari mumkin - addPassenger(Yo'lovchi yo'lovchisi) , shunga qaramay, mashina to'g'ri ishlashda davom etadi. O'z navbatida, Passenger ob'ektlari Car ob'ektisiz mavjud bo'lishi mumkin . Siz tushunganingizdek, bu biz kompozitsiyada ko'rganimizdan ko'ra ancha zaifroq aloqadir. Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish.  14-3-qismLekin bu hammasi emas, boshqasiga agregatsiya yo‘li bilan bog‘langan ob’ekt ayni vaqtda boshqa ob’ektlar bilan ham berilgan bog‘lanishga ega bo‘lishi mumkin. Masalan, siz Java talabasi sifatida ingliz tili, OOP va logarifm kurslariga bir vaqtning o'zida o'qiyapsiz, lekin ayni paytda siz ularning muhim qismi emassiz, ularsiz normal ishlash mumkin emas (masalan, o'qituvchi).

3. Siz amalda qanday GoF naqshlaridan foydalangansiz? Misollar keltiring.

Men bu savolga allaqachon javob berganman, shuning uchun tahlilga havolani qoldiraman , birinchi savolga qarang. Shuningdek, men dizayn naqshlari bo'yicha ajoyib maqola topdim , uni qo'lda saqlashni maslahat beraman.

4. Proksi-server obyekti nima? Misollar keltiring

Proksi-server - bu haqiqiy ob'ektlar o'rniga maxsus o'rnini bosuvchi ob'ektlarni yoki boshqacha aytganda, proksi-server ob'ektlarini almashtirishga imkon beruvchi strukturaviy dizayn namunasi. Ushbu proksi-server ob'ektlari asl ob'ektga qo'ng'iroqlarni ushlab turadi, bu esa qo'ng'iroqni asl ob'ektga uzatishdan oldin yoki keyin ba'zi mantiqlarni kiritish imkonini beradi. Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish.  14-4-qismProksi-serverdan foydalanishga misollar:
  • Masofaviy proksi sifatida - mahalliy sifatida taqdim etilishi kerak bo'lgan uzoq ob'ektga (boshqa manzil maydonidagi ob'ekt) kerak bo'lganda foydalaniladi. Bunday holda, proksi-server ulanishni yaratish, kodlash, dekodlash va hokazolarni bajaradi, mijoz esa uni mahalliy bo'shliqda joylashgan asl ob'ekt kabi ishlatadi.

  • Virtual proksi sifatida - resurs talab qiladigan ob'ekt kerak bo'lganda ishlatiladi. Bunday holda, proksi ob'ekt hali mavjud bo'lmagan haqiqiy ob'ektning tasviri kabi xizmat qiladi. Ushbu ob'ektga haqiqiy so'rov (usul chaqiruvi) yuborilganda, faqat keyin asl ob'ekt yuklanadi va usul bajariladi. Ushbu yondashuv dangasa ishga tushirish deb ham ataladi; bu juda qulay bo'lishi mumkin, chunki ba'zi hollarda asl ob'ekt foydali bo'lmasligi mumkin va keyin uni yaratish uchun hech qanday xarajat bo'lmaydi.

  • Xavfsizlik proksi-serveri sifatida - mijoz huquqlari asosida ba'zi ob'ektga kirishni boshqarish kerak bo'lganda foydalaniladi. Ya'ni, agar kirish huquqiga ega bo'lmagan mijoz asl ob'ektga kirishga harakat qilsa, proksi-server uni ushlab turadi va ruxsat bermaydi.

Keling, virtual proksi-server misolini ko'rib chiqaylik: Bizda ishlov beruvchi interfeysi mavjud:
public interface Processor {
 void process();
}
Amalga oshirish juda ko'p resurslardan foydalanadi, lekin shu bilan birga u har safar ishga tushirilganda ishlatilmasligi mumkin:
public class HiperDifficultProcessor implements Processor {
 @Override
 public void process() {
   // некоторый сверхсложная обработка данных
 }
}
Proksi klassi:
public class HiperDifficultProcessorProxy implements Processor {
private HiperDifficultProcessor processor;

 @Override
 public void process() {
   if (processor == null) {
     processor = new HiperDifficultProcessor();
   }
   processor.process();
 }
}
Keling, uni asosiyda ishga tushiramiz :
Processor processor = new HiperDifficultProcessorProxy();
// тут тяжеловсеного оригинального an object, ещё не сущетсвует
// но при этом есть an object, который его представляет и у которого можно вызывать его методы
processor.process(); // лишь теперь, an object оригинал был создан
Shuni ta'kidlaymanki, ko'plab ramkalar proksi-serverdan foydalanadi va bahor uchun bu asosiy naqshdir (bahor u bilan ichkarida va tashqarida tikilgan). Ushbu naqsh haqida ko'proq ma'lumotni bu erda o'qing . Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish.  14-5-qism

5. Java 8 da qanday yangiliklar e'lon qilindi?

Java 8 tomonidan kiritilgan innovatsiyalar quyidagilardan iborat:
  • Funktsional interfeyslar qo'shildi, bu erda qanday hayvon haqida o'qing .

  • Funktsional interfeyslar bilan chambarchas bog'liq bo'lgan Lambda ifodalari, ulardan foydalanish haqida ko'proq ma'lumotni bu erda o'qing .

  • Ma'lumotlar to'plamini qulay qayta ishlash uchun Stream API qo'shildi , bu erda batafsil o'qing .

  • Usullarga havolalar qo'shildi .

  • ForEach() usuli Iterable interfeysiga qo'shildi .

  • Java.time paketiga yangi sana va vaqt API qo'shildi, bu erda batafsil tahlil .

  • Yaxshilangan bir vaqtning o'zida API .

  • Null qiymatlarni to'g'ri ishlash uchun ishlatiladigan ixtiyoriy o'rash sinfini qo'shsangiz , ushbu mavzu bo'yicha ajoyib maqolani bu yerda topishingiz mumkin .

  • Interfeyslar uchun statik va standart usullardan foydalanish qobiliyatini qo'shish (bu mohiyatan Java-ni bir nechta merosga yaqinlashtiradi), bu erda batafsilroq ma'lumot .

  • Collection(removeIf(), spliterator()) sinfiga yangi usullar qo'shildi .

  • Java Core uchun kichik yaxshilanishlar.

Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish.  14-6-qism

6. Yuqori uyg'unlik va past bog'lanish nima? Misollar keltiring.

Yuqori uyg'unlik yoki yuqori uyg'unlik - bu ma'lum bir sinfda bir-biri bilan chambarchas bog'liq bo'lgan va maqsadlari uchun birlashtirilgan elementlar mavjud bo'lgan tushuncha. Masalan, User sinfidagi barcha usullar foydalanuvchi xatti-harakatlarini ifodalashi kerak. Agar sinf o'zaro bog'liq bo'lmagan elementlarni o'z ichiga olgan bo'lsa, u past uyg'unlikka ega. Masalan, elektron pochta manzilini tekshirish usulini o'z ichiga olgan Foydalanuvchi sinfi:
public class User {
private String name;
private String email;

 public String getName() {
   return this.name;
 }

 public void setName(final String name) {
   this.name = name;
 }

 public String getEmail() {
   return this.email;
 }

 public void setEmail(final String email) {
   this.email = email;
 }

 public boolean isValidEmail() {
   // некоторая логика валидации емейла
 }
}
Foydalanuvchi sinfi foydalanuvchining elektron pochta manzilini saqlash uchun javobgar bo'lishi mumkin, lekin uni tasdiqlash yoki elektron pochta xabarini yuborish uchun emas. Shuning uchun, yuqori muvofiqlikka erishish uchun biz tekshirish usulini alohida yordamchi sinfga o'tkazamiz:
public class EmailUtil {
 public static boolean isValidEmail(String email) {
   // некоторая логика валидации емейла
 }
}
Va biz uni kerak bo'lganda ishlatamiz (masalan, foydalanuvchini saqlashdan oldin). Low Coupling yoki Low Coupling - bu dasturiy modullar orasidagi past o'zaro bog'liqlikni tavsiflovchi tushuncha. Aslida, o'zaro bog'liqlik - bu birini o'zgartirish ikkinchisini o'zgartirishni talab qiladi. Ikki sinf, agar ular bir-biri bilan chambarchas bog'liq bo'lsa, kuchli ulanishga (yoki qattiq ulanishga) ega. Masalan, bir-biriga havolalarni saqlaydigan va bir-birining usullarini chaqiradigan ikkita aniq sinf. Bo'shashgan sinflarni rivojlantirish va saqlash osonroq. Ular bir-biridan mustaqil bo'lgani uchun ular parallel ravishda ishlab chiqilishi va sinovdan o'tkazilishi mumkin. Bundan tashqari, ular bir-biriga ta'sir qilmasdan o'zgartirilishi va yangilanishi mumkin. Keling, kuchli bog'langan sinflarning misolini ko'rib chiqaylik. Bizda talabalar sinfi bor:
public class Student {
 private Long id;
 private String name;
 private List<Lesson> lesson;
}
Unda darslar ro'yxati mavjud:
public class Lesson {
 private Long id;
 private String name;
 private List<Student> students;
}
Har bir darsda ishtirok etayotgan talabalarga havola mavjud. Ajablanarli darajada kuchli ushlash, shunday emasmi? Uni qanday kamaytirish mumkin? Birinchidan, talabalarda fanlar ro'yxati emas, balki ularning identifikatorlari ro'yxati borligiga ishonch hosil qilaylik:
public class Student {
 private Long id;
 private String name;
 private List<Long> lessonIds;
}
Ikkinchidan, dars sinfi barcha talabalar haqida bilishi shart emas, shuning uchun ularning ro'yxatini butunlay o'chirib tashlaymiz:
public class Lesson {
 private Long id;
 private String name;
}
Shunday qilib, bu ancha osonlashdi va aloqa ancha zaiflashdi, shunday emasmi? Java dasturchisi uchun intervyudan olingan savollar va javoblarni tahlil qilish.  14-7-qism

OOP

7. Java-da bir nechta merosni qanday amalga oshirish mumkin?

Ko'p meros - ob'ektga yo'naltirilgan kontseptsiyaning xususiyati bo'lib, unda sinf bir nechta ota-klassning xususiyatlarini meros qilib olishi mumkin. Muammo super sinfda ham, kichik sinfda ham bir xil imzoga ega usullar mavjud bo'lganda paydo bo'ladi. Metodni chaqirganda, kompilyator qaysi sinf usulini chaqirish kerakligini aniqlay olmaydi va hatto ustunlikka ega bo'lgan sinf usulini chaqirganda ham. Shuning uchun Java bir nechta merosni qo'llab-quvvatlamaydi! Ammo qandaydir bo'shliq bor, biz bu haqda keyinroq gaplashamiz. Yuqorida aytib o'tganimdek, Java 8-ning chiqarilishi bilan interfeyslarga standart usullarga ega bo'lish imkoniyati qo'shildi . Agar interfeysni amalga oshiruvchi sinf ushbu usulni bekor qilmasa, u holda ushbu standart dastur qo'llaniladi (mavhum usulni amalga oshirish kabi standart usulni bekor qilish shart emas). Bunday holda, bir sinfda turli xil interfeyslarni amalga oshirish va ularning standart usullaridan foydalanish mumkin. Keling, bir misolni ko'rib chiqaylik. Bizda standart fly() usuli bilan flayer interfeysi mavjud :
public interface Flyer {
 default void fly() {
   System.out.println("Я лечу!!!");
 }
}
Walker interfeysi, standart walk() usuli bilan :
public interface Walker {
 default void walk() {
   System.out.println("Я хожу!!!");
 }
}
Swimmer interfeysi, swim() usuli bilan :
public interface Swimmer {
 default void swim() {
   System.out.println("Я плыву!!!");
 }
}
Xo'sh, keling, bularning barchasini bitta o'rdak sinfida amalga oshiramiz:
public class Duck implements Flyer, Swimmer, Walker {
}
Keling, o'rdakimizning barcha usullarini ishlataylik:
Duck donald = new Duck();
donald.walk();
donald.fly();
donald.swim();
Konsolda biz quyidagilarni olamiz:
Men boraman!!! Men uchaman !!! Men suzaman!!!
Bu shuni anglatadiki, biz bir nechta merosni to'g'ri tasvirladik, garchi u bunday bo'lmasa ham. Разбор вопросов и ответов с собеседований на Java-разработчика. Часть 14 - 8Shuni ham ta'kidlaymanki, agar sinf ushbu usullarda bir xil usul nomlari va bir xil argumentlarga ega bo'lgan standart usullar bilan interfeyslarni amalga oshirsa, kompilyator mos kelmasligi haqida shikoyat qila boshlaydi, chunki u haqiqatan ham qaysi usuldan foydalanish kerakligini tushunmaydi. Chiqishning bir necha yo'li mavjud:
  • Interfeyslardagi usullarni bir-biridan farq qiladigan tarzda qayta nomlang.
  • Amalga oshirish sinfida bunday bahsli usullarni bekor qiling.
  • Ushbu bahsli usullarni qo'llaydigan sinfdan meros oling (keyin sizning sinfingiz aynan uni amalga oshirishdan foydalanadi).

8. Final, final va finalize() usullarining farqi nimada?

final - bu sinf, usul yoki o'zgaruvchiga cheklov qo'yish uchun ishlatiladigan kalit so'z, cheklov ma'nosi:
  • O'zgaruvchi uchun - dastlabki ishga tushirilgandan so'ng, o'zgaruvchini qayta aniqlab bo'lmaydi.
  • Usul uchun usulni pastki sinfda (voris sinfida) bekor qilib bo'lmaydi.
  • Sinf uchun - sinfni meros qilib bo'lmaydi.
Nihoyat, bu kod bloki oldidagi kalit so'z bo'lib, istisnolar bilan ishlashda, try bloki bilan birgalikda va catch bloki bilan birga (yoki bir-birining o'rnida) ishlatiladi. Ushbu blokdagi kod har qanday holatda, istisno o'rnatilgan yoki yo'qligidan qat'i nazar, bajariladi. Maqolaning ushbu qismida , 104-savolda, ushbu blok bajarilmaydigan istisno holatlar muhokama qilinadi. finalize() ob'ekt sinfining usuli bo'lib , har bir ob'ekt axlat yig'uvchi tomonidan o'chirilishidan oldin chaqiriladi, bu usul (oxirgi) deb ataladi va egallab olingan resurslarni tozalash uchun ishlatiladi. Har bir ob'ekt meros qilib oladigan Object sinfining usullari haqida ko'proq ma'lumot olish uchun maqolaning ushbu qismidagi 11-savolga qarang . Xo'sh, bugun biz shu bilan yakunlaymiz. Keyingi qismda ko'rishguncha! Разбор вопросов и ответов с собеседований на Java-разработчика. Часть 14 - 9
Izohlar
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION