Java Exception(Anti-Pattern)
توضیحات جلسه
جزوه و مستندات
مفاهیم کلیدی
- Anti-Pattern
الگوهای رایجی در برنامهنویسی هستند که در ظاهر راهکار به نظر میرسند، اما در عمل باعث ایجاد مشکل، پیچیدگی و دشوار شدن فرایند عیبیابی (Debugging) میشوند.
- Catching General Exception
استفاده از کلاس پایه Exception در بلوک catch، به جای استفاده از استثناهای اختصاصی مانند ArithmeticException. این کار باعث ابهام در کد و دشواری در شناسایی نوع دقیق خطا میشود.
- Swallowing Exception
اصطلاحی به معنای خفه کردن یا بلعیدن استثنا است. این وضعیت زمانی رخ میدهد که یک Exception در بلوک catch دریافت شود، اما هیچ واکنشی مانند نمایش خطا یا ثبت لاگ به آن نشان داده نشود و برنامه بهسادگی از کنار آن عبور کند.
- Finally Block
بلوک کدی است که پس از try و catch اجرا میشود. استفاده از دستوراتی که روند اجرای برنامه را تغییر میدهند، مانند return، در این بلوک یک Anti-Pattern جدی محسوب میشود.
- Flow Control
به معنای مدیریت مسیر اجرای برنامه است. استفاده از سیستم Exception برای کنترل منطق برنامه، به جای ساختارهای شرطی مانند if و else، یک اشتباه فنی محسوب میشود.
- Stack Trace
گزارشی است که ترتیب فراخوانی متدها را هنگام بروز خطا نشان میدهد و برای پیدا کردن منشأ اصلی مشکل در کد اهمیت زیادی دارد.
موارد مصاحبه ای
- چرا استفاده از
Exceptionبه صورت کلی (General) در بلاکcatchبد است؟
این کار باعث مبهم شدن کد میشود. برنامهنویس بعدی نمیداند دقیقاً چه خطای مشخصی قرار است مدیریت شود. همچنین ممکن است استثناهای غیرمنتظرهای که باید باعث توقف برنامه شوند، بهاشتباه مدیریت شده و پنهان بمانند.
- خفه کردن اکسپشن (Swallowing Exception) چه خطراتی دارد؟
این کار میتواند رفتار برنامه را غیرقابلپیشبینی کند. برای مثال، اگر هنگام بروز خطا یک مقدار تصادفی یا ثابت، مانند 160، برگردانده شود، کاربر یا سیستمهای دیگر تصور میکنند عملیات با موفقیت انجام شده است؛ درحالیکه در واقعیت خطایی رخ داده است.
- تأثیر استفاده از
returnدر بلاکfinallyچیست؟
استفاده از return در این بلوک باعث میشود مقدار بازگشتیِ بلوکهای try یا catch بازنویسی (Override) شود. خطرناکتر اینکه اگر استثنایی پرتاب شده باشد، دستور return در finally باعث سرکوب و از بین رفتن آن استثنا میشود و برنامه بهصورت عادی ادامه پیدا میکند.
- چرا نباید از
throwبه عنوان جایگزینgotoاستفاده کرد؟
استثناها برای مدیریت شرایط غیرمنتظره و خطاها طراحی شدهاند. استفاده از آنها برای هدایت روند اجرای برنامه (Flow Control) باعث پیچیدگی غیرضروری و کاهش خوانایی و کارایی کد میشود.
سناریو کاربردی
در یک برنامه تقسیم اعداد، اگر کاربر عدد صفر را وارد کند، ArithmeticException رخ میدهد.
- رویکرد اشتباه ۱: گرفتن کلاس
Exceptionبه صورت کلی
در این حالت، اگر خطای دیگری، مانند خطای حافظه، رخ دهد، همان بلوک catch آن را نیز مدیریت میکند؛ درحالیکه چنین رفتاری صحیح نیست.
- رویکرد اشتباه ۲: بلعیدن خطا
اگر بلوک catch را خالی بگذاریم، برنامه بدون ارائه هیچ توضیحی به کار خود پایان میدهد و کاربر متوجه نمیشود چرا خروجی دریافت نکرده است.
- رویکرد اشتباه ۳: برگرداندن مقدار غلط
اگر هنگام بروز خطا مقدار ثابتی مانند 0 برگردانیم، محاسبات بعدی بر اساس دادهای نادرست و پنهان انجام میشوند.
- رویکرد اشتباه ۴: استفاده نادرست از
finally
اگر در بلوک finally مقدار 100 را با دستور return برگردانیم، حتی اگر تقسیم بهدرستی انجام شده و نتیجه 5 باشد، متد همیشه مقدار 100 را برمیگرداند.
بیشتر بدانید
- IDE Tip
در محیط IntelliJ IDEA، اگر از دستور return داخل بلوک finally استفاده کنید، خود IDE به شما هشدار (Warning) میدهد. این هشدار نشان میدهد که چنین کاری باعث میشود متد بهصورت عادی به پایان نرسد (finally block cannot complete normally).
- فلسفه کدنویسی (Clean Code)
همیشه کدی بنویسید که برای توسعهدهنده بعدی، خوانا و شفاف باشد. هدف این است که منطق برنامه، نحوه مدیریت خطا و مسیر اجرای کد بدون ابهام قابل درک و نگهداری باشد.
- توصیه فنی
به جای کنترل روند اجرای برنامه با Exception، از شرطهای ساده مانند if استفاده کنید. Exceptionها باید فقط برای رخدادهای استثنایی و خطاهای واقعی سیستم به کار گرفته شوند.
