CodeGym /وبلاگ جاوا /Random-FA /روش های پیش فرض در رابط ها
John Squirrels
مرحله
San Francisco

روش های پیش فرض در رابط ها

در گروه منتشر شد
هر نسخه جدید جاوا با نسخه های قبلی متفاوت است. در اینجا نمونه ای از تغییرات در موادی است که ما پوشش داده ایم: قبل از جاوا 5، زبان s نداشت enum. روش های پیش فرض در رابط ها - 1به طور مشابه، جاوا 8 به طور قابل توجهی با جاوا 7 متفاوت است. بیشتر درس های ما برای نسخه هفتم این زبان نوشته شده است، اما البته ما نوآوری های مهم را نادیده نخواهیم گرفت. از آنجایی که ما قبلاً در مورد رابط ها در این درس صحبت می کنیم، یک به روز رسانی را در نظر خواهیم گرفت - روش های پیش فرض در رابط ها . شما قبلاً می دانید که یک رابط رفتار را پیاده سازی نمی کند . وظیفه آن توصیف رفتاری است که تمام اشیایی که آن را پیاده سازی می کنند باید داشته باشند . اما توسعه‌دهندگان اغلب با موقعیت‌هایی مواجه می‌شوند که پیاده‌سازی یک متد در همه کلاس‌ها یکسان است. بیایید نمونه ماشین قدیمی خود را در نظر بگیریم:

public interface Car {

   public void gas();

   public void brake();
}
public class Sedan implements Car {

   @Override
   public void gas() {
       System.out.println("Gas!");
   }

   @Override
   public void brake() {
       System.out.println("Brake!");
   }
}


public class Truck implements Car {

   @Override
   public void gas() {
       System.out.println("Gas!");
   }

   @Override
   public void brake() {
       System.out.println("Brake!");
   }
}


public class F1Car implements Car {
   @Override
   public void gas() {
       System.out.println("Gas!");
   }

   @Override
   public void brake() {
       System.out.println("Brake!");
   }
}
"به نظر شما مشکل اصلی این کد چیست؟ احتمالاً متوجه شده اید که ما یکسری کدهای تکراری نوشتیم! این مشکل در برنامه نویسی رایج است و باید از آن اجتناب کنید. این مسئله دیگری است که قبلاً راه حل های خاصی وجود نداشت. جاوا 8 منتشر شد. با این نسخه توانایی تعیین روش های پیش فرض و پیاده سازی آنها در داخل رابط وجود داشت! در اینجا نحوه انجام این کار به شرح زیر است:

public interface Car {

   public default void gas() {
       System.out.println("Gas!");
   }

   public default void brake() {
       System.out.println("Brake!");
   }
}

public class Sedan implements Car {

}

public class Truck implements Car {

}

public class F1Car implements Car {

}
اکنون gas()و brake()متدهایی که برای همه خودروها یکسان بود به رابط منتقل شده است. نیازی به کد تکراری نیست. علاوه بر این، متدها در هر کلاس موجود هستند!

public class Main {

   public static void main(String[] args) {

       F1Car f1Car = new F1Car();
       Sedan sedan = new Sedan();
       Truck truck = new Truck();
       truck.gas();
       sedan.gas();
       f1Car.brake();
   }
}
اگر 100 کلاس با gas()متد وجود داشته باشد، اما فقط 99 تای آنها رفتار مشابهی داشته باشند، چه؟ آیا این همه چیز را خراب می کند و روش پیش فرض را برای این وضعیت نامناسب می کند؟ البته نه :) روش های پیش فرض در اینترفیس ها را می توان مانند روش های معمولی باطل کرد.

public class UnusualCar implements Car {
   @Override
   public void gas() {
       System.out.println("This car accelerates differently!");
   }

   @Override
   public void brake() {
       System.out.println("This car decelerates differently!");
   }
}
تمام 99 نوع خودروی دیگر روش پیش‌فرض را اجرا می‌کنند و کلاس UnusualCar، که یک استثناست، تصویر کلی را خراب نمی‌کند و با آرامش رفتار خود را تعریف می‌کند. وراثت چندگانه رابط ها. همانطور که می دانید جاوا از وراثت چندگانه پشتیبانی نمی کند. دلایل زیادی برای این وجود دارد. ما آنها را در یک درس جداگانه به تفصیل بررسی خواهیم کرد. زبان های دیگر مانند C++ از آن پشتیبانی می کنند. بدون وراثت چندگانه، یک مشکل جدی ایجاد می شود: یک شی می تواند چندین ویژگی و «رفتار» متفاوت داشته باشد. در اینجا مثالی از زندگی آورده شده است: ما برای والدین خود کودک هستیم، برای معلمان خود دانش آموزان و برای پزشکان خود بیمار هستیم. در زندگی، ما نقش‌های متفاوتی را بر عهده می‌گیریم و بر این اساس، رفتارهای متفاوتی از خود نشان می‌دهیم: بدیهی است که همانطور که با دوستان نزدیک خود صحبت می‌کنیم، با معلمان صحبت نمی‌کنیم. بیایید سعی کنیم این را به کد ترجمه کنیم. تصور کنید که ما دو کلاس داریم: Pond و Aviary. برای استخر، ما به مرغ آبی نیاز داریم. برای پرندگان به پرنده های پرنده نیاز داریم. برای انجام این کار، ما دو کلاس پایه ایجاد کرده ایم: FlyingBirdو Waterfowl.

public class Waterfowl {
}

public class FlyingBird {
}
بر این اساس، ما پرندگانی را که طبقات آنها ارث می برند FlyingBirdبه پرنده و پرندگانی را که ارث می برند Waterfowlبه حوضچه می فرستیم. همه چیز خیلی ساده به نظر می رسد. اما اردک را کجا بفرستیم؟ شنا می کند و پرواز می کند. و ارث چندگانه نداریم. خوشبختانه جاوا از پیاده سازی چندگانه رابط ها پشتیبانی می کند. اگرچه یک کلاس نمی تواند چندین والدین را به ارث ببرد، می تواند به راحتی چندین رابط را پیاده سازی کند! اردک ما می تواند هم پرنده پرنده باشد و هم یک پرنده آبزی :) برای رسیدن به نتیجه دلخواه ما فقط به ساختن FlyingBirdو Waterfowlواسط نیاز داریم تا کلاس ها.

public class Duck implements FlyingBird, Waterfowl {

   // The methods of both interfaces can be easily combined into one class

   @Override
   public void fly() {
       System.out.println("Fly!");
   }

   @Override
   public void swim() {

       System.out.println("Swim!");
   }
}
بر این اساس، برنامه ما انعطاف پذیری کلاس ها را حفظ می کند و در ترکیب با روش های پیش فرض، توانایی ما برای تعریف رفتار اشیا تقریبا نامحدود می شود! :)
نظرات
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION