جلسه شماره 120رایگان

JavaBeans Pattern in Java | الگوی جاوا بین در جاوا

00:11:07

توضیحات جلسه

🎥 این ویدیو سومین قسمت از پلی‌لیست بررسی کتاب Effective Java است. 📚 در این جلسه از مسیر یادگیری اصول طراحی حرفه‌ای در جاوا، سراغ یکی از مباحث بسیار مهم و بحث‌برانگیز در آیتم دوم کتاب می‌رویم: بررسی الگوی JavaBeans Pattern. در این ویدیو به طور عمیق بررسی می‌کنیم که الگوی JavaBeans چیست، چگونه کار می‌کند و چرا با وجود کاربرد گسترده، می‌تواند چالش‌های بزرگی در طراحی کلاس‌های شما ایجاد کند. ما به دنبال این هستیم که یاد بگیریم چگونه از اشتباهات رایج در طراحی کلاس‌ها جلوگیری کنیم و به سمت نوشتن کدهای ایمن‌تر و قابل‌اعتمادتر حرکت کنیم. در این جلسه یاد می‌گیریم: 🔍 تعریف دقیق JavaBeans Pattern و نحوه پیاده‌سازی آن ✅ بررسی مزایا و دلایل محبوبیت این الگو در پروژه‌ها ⚠️ تحلیل معایب جدی و چالش‌های طراحی با استفاده از این الگو 🛠️ بررسی روش‌های کاهش بخشی از مشکلات (Partial Mitigation) این الگو 🧠 جمع‌بندی نکات کلیدی و راهکارهای جایگزین برای طراحی بهتر اگر می‌خواهید از یک برنامه‌نویس معمولی به یک متخصص جاوا تبدیل شوید، درک عمیق این الگوها و شناخت رفتارهای غیرمنتظره در طراحی کلاس‌ها یکی از مهم‌ترین گام‌ها برای شما خواهد بود. 🔗 لینک دانلود کتاب افکتیو جاوا: https://github.com/farzadafi/Teaching/blob/master/Book/EffectiveJava/2018-Effective%20Java.pdf 📌 یوتیوب: youtube.com/@farzadafi 📌 آپارات: aparat.com/farzadafi 📌 وب سایت: https://farzadafi.ir 💬 گروه پرسش و پاسخ تلگرام: programmingByFarzadAfi@ 💬 گروه پرسش و پاسخ بله: @programming_by_farzadafi هر سوالی داشته باشید می‌توانید در گروه بپرسید تا من یا مربی‌های گروه کمکتان کنیم :)

جزوه و مستندات

مفاهیم کلیدی

  • JavaBeans Pattern

رویکردی در ساخت شیء که در آن ابتدا نمونه شیء با استفاده از یک constructor بدون پارامتر ساخته می‌شود و سپس فیلدهای اجباری و اختیاری از طریق متدهای setter مقداردهی می‌شوند.

  • Inconsistent State

وضعیتی ناپایدار که در آن ساخت شیء بین چند فراخوانی متد تقسیم می‌شود و قبل از مقداردهی تمام فیلدهای لازم، شیء در حافظه وجود دارد اما داده‌های آن ناقص یا نامعتبر هستند.

  • Telescoping Constructor Pattern

الگویی سنتی که در آن چندین constructor با تعداد پارامترهای مختلف تعریف می‌شوند؛ الگوی JavaBeans برای حل خوانایی پایین این الگو ارائه شد اما معایب جدیدی ایجاد کرد.

  • Immutability

قابلیت تغییرناپذیری شیء پس از ساخت؛ الگوی JavaBeans به‌دلیل وجود متدهای setter عمومی، امکان پیاده‌سازی کلاس‌های immutable را به‌طور کامل از بین می‌برد.

  • Thread Safety

امنیت چندنخی که در الگوی JavaBeans به دلیل ماهیت mutable بودن اشیاء و امکان تغییر وضعیت هم‌زمان توسط چندین thread، به‌خطر می‌افتد.

  • Object Freezing

تکنیکی دستی برای قفل کردن شیء پس از پایان فراخوانی متدهای setter به منظور جلوگیری از تغییرات بعدی؛ این روش به دلیل عدم امکان بررسی توسط کامپایلر، مستعد خطای runtime است و در عمل کاربرد کمی دارد.

موارد مصاحبه ای

  • مزیت اصلی الگوی JavaBeans نسبت به الگوی Telescoping Constructor چیست؟

خوانایی بالاتر کد در زمان ساخت شیء و عدم نیاز به پاس دادن مقادیر پیش‌فرض یا تکراری به constructorهای طولانی و تودرتو.

  • چرا الگوی JavaBeans خطر ایجاد وضعیت ناسازگار (Inconsistent State) دارد؟

زیرا فرآیند ساخت شیء به چندین دستور مستقل تقسیم می‌شود و ممکن است قبل از فراخوانی تمام متدهای setter، شیء توسط بخش دیگری از برنامه استفاده شود، در حالی که فیلدهای اجباری آن هنوز مقداردهی نشده‌اند.

  • چرا الگوی JavaBeans مانع از ایجاد اشیاء Immutable می‌شود؟

چون برای مقداردهی فیلدها حتماً باید متدهای setter عمومی در کلاس وجود داشته باشند که امکان تغییر وضعیت شیء را در هر لحظه از چرخه حیات آن باز می‌گذارد.

  • چرا اعتبارسنجی پارامترها در الگوی JavaBeans دشوارتر از Constructor است؟

در constructor می‌توان تمام پارامترها را در یک مرحله قبل از ساخت شیء اعتبارسنجی کرد؛ اما در JavaBeans اعتبارسنجی وابستگی بین فیلدها امکان‌پذیر نیست زیرا ترتیب فراخوانی setterها مشخص نیست.

  • چرا تکنیک دستی Freezing راه‌حل مناسبی برای مشکل Mutability در JavaBeans نیست؟

چون کامپایلر هیچ تضمینی نمی‌دهد که برنامه‌نویس حتماً متد freeze را قبل از استفاده از شیء صدا بزند و خطاهای حاصل از آن در زمان runtime ظاهر می‌شوند.

سناریو کاربردی

  • پیاده‌سازی کلاس بر اساس الگوی JavaBeans و نحوه مقداردهی آن

تعریف کلاس با مقادیر پیش‌فرض و متدهای setter:

public class NutritionFacts {
    private int servingSize  = -1; // Required; no default value
    private int servings     = -1; // Required; no default value
    private int calories     = 0;
    private int fat          = 0;
    private int sodium       = 0;
    private int carbohydrate = 0;

    public NutritionFacts() { }

    public void setServingSize(int val)  { servingSize = val; }
    public void setServings(int val)     { servings = val; }
    public void setCalories(int val)     { calories = val; }
    public void setFat(int val)          { fat = val; }
    public void setSodium(int val)       { sodium = val; }
    public void setCarbohydrate(int val) { carbohydrate = val; }
}

نحوه ساخت شیء و مقداردهی زنجیره‌ای:

NutritionFacts cocaCola = new NutritionFacts();
cocaCola.setServingSize(240);
cocaCola.setServings(8);
cocaCola.setCalories(100);
cocaCola.setSodium(35);
cocaCola.setCarbohydrate(27);

اگر فراخوانی متد setServingSize یا setServings فراموش شود، شیء cocaCola با مقادیر پیش‌فرض نامعتبر (-1) در برنامه گردش می‌کند و کامپایلر هیچ خطایی صادر نخواهد کرد.

بیشتر بدانید

  • خطر خطایابی در Inconsistent State

خطاهایی که به دلیل استفاده از شیء ناقص در الگوی JavaBeans رخ می‌دهند، معمولاً در نقاطی دور از محل ساخت شیء ایجاد می‌شوند و ردیابی ریشه خطا (root cause) را بسیار سخت می‌کنند.

  • تداخل با اصول کپسوله‌سازی

ارائه متدهای setter برای تمام فیلدها عملاً کنترل وضعیت داخلی کلاس را از بین برده و کپسوله‌سازی را تضعیف می‌کند.

  • جایگزین پیشنهادی (Builder Pattern)

برای رفع هم‌زمان مشکل خوانایی Telescoping Constructor و مشکلات ایمنی و Mutability در JavaBeans، استفاده از الگوی طراحی Builder پیشنهاد می‌شود.