1. ব্যতিক্রমের ধরন

সমস্ত ব্যতিক্রমগুলি 4 প্রকারে বিভক্ত, যা আসলে এমন শ্রেণী যা একে অপরের উত্তরাধিকারী।
Throwable
ক্লাস
সব ব্যতিক্রমের জন্য বেস ক্লাস হল Throwable
ক্লাস। ক্লাসে Throwable
এমন কোড রয়েছে যা একটি অ্যারেতে বর্তমান কল স্ট্যাক (বর্তমান পদ্ধতির স্ট্যাক ট্রেস) লেখে। আমরা একটু পরে শিখব একটি স্ট্যাক ট্রেস কি.
থ্রো অপারেটর শুধুমাত্র ক্লাস থেকে উদ্ভূত একটি বস্তু গ্রহণ করতে পারে Throwable
। এবং যদিও আপনি তাত্ত্বিকভাবে কোড লিখতে পারেন throw new Throwable();
, কেউ সাধারণত এটি করে না। ক্লাসের মূল উদ্দেশ্য Throwable
হল সকল ব্যতিক্রমের জন্য একটি একক অভিভাবক শ্রেণী থাকা।
Error
ক্লাস
পরবর্তী ব্যতিক্রম ক্লাস হল Error
ক্লাস, যা সরাসরি Throwable
ক্লাসের উত্তরাধিকারী হয়। গুরুতর সমস্যা দেখা দিলে জাভা মেশিন ক্লাসের Error
(এবং এর বংশধরদের) বস্তু তৈরি করে । উদাহরণস্বরূপ, একটি হার্ডওয়্যার ত্রুটি, অপর্যাপ্ত মেমরি, ইত্যাদি।
সাধারণত, একজন প্রোগ্রামার হিসাবে, আপনি এমন পরিস্থিতিতে কিছুই করতে পারেন নাError
যেখানে প্রোগ্রামে এই জাতীয় ত্রুটি (যে ধরনের জন্য একটি নিক্ষেপ করা উচিত) ঘটেছে: এই ত্রুটিগুলি খুব গুরুতর। আপনি যা করতে পারেন তা হল ব্যবহারকারীকে জানানো যে প্রোগ্রামটি ক্র্যাশ হচ্ছে এবং/অথবা প্রোগ্রাম লগে ত্রুটি সম্পর্কে সমস্ত পরিচিত তথ্য লিখুন।
Exception
ক্লাস
এবং ক্লাসগুলি হল সাধারণ ত্রুটিগুলির জন্য যা প্রচুর পদ্ধতির অপারেশনে ঘটে Exception
। প্রতিটি নিক্ষিপ্ত ব্যতিক্রমের লক্ষ্য হল একটি ব্লক দ্বারা ধরা যা সঠিকভাবে এটি পরিচালনা করতে জানে।RuntimeException
catch
যখন কোনো পদ্ধতি কোনো কারণে তার কাজ সম্পূর্ণ করতে পারে না, তখন তা অবিলম্বে উপযুক্ত প্রকারের ব্যতিক্রম ছুড়ে কলিং পদ্ধতিকে অবহিত করা উচিত।
অন্য কথায়, একটি ভেরিয়েবল সমান হলে null
, পদ্ধতিটি একটি নিক্ষেপ করবে NullPointerException
। যদি ভুল আর্গুমেন্ট পদ্ধতিতে পাস করা হয়, তাহলে এটি একটি নিক্ষেপ করবে InvalidArgumentException
। যদি পদ্ধতিটি ঘটনাক্রমে শূন্য দ্বারা ভাগ করে তবে এটি একটি নিক্ষেপ করবে ArithmeticException
।
RuntimeException
ক্লাস
RuntimeExceptions
এর একটি উপসেট Exceptions
। আমরা এমনকি বলতে পারি যে RuntimeException
এটি সাধারণ ব্যতিক্রমগুলির একটি হালকা সংস্করণ ( Exception
) — এই ধরনের ব্যতিক্রমগুলিতে কম প্রয়োজনীয়তা এবং বিধিনিষেধ আরোপ করা হয়
আপনি পরে Exception
এবং এর মধ্যে পার্থক্য শিখবেন ।RuntimeException
2. Throws
: চেক করা ব্যতিক্রম
সমস্ত জাভা ব্যতিক্রম 2টি বিভাগে পড়ে: চেক করা এবং আনচেক করা ।
সমস্ত ব্যতিক্রম যা উত্তরাধিকারসূত্রে প্রাপ্ত RuntimeException
বা আনচেক করা ব্যতিক্রমError
হিসাবে বিবেচিত হয় । অন্য সব ব্যতিক্রম চেক করা হয় .
চেক করা ব্যতিক্রমগুলি চালু হওয়ার 20 বছর পরে, প্রায় প্রতিটি জাভা প্রোগ্রামার এটিকে একটি বাগ হিসাবে মনে করে। জনপ্রিয় আধুনিক ফ্রেমওয়ার্কগুলিতে, সমস্ত ব্যতিক্রমগুলির 95% আনচেক করা হয়। C# ভাষা, যা জাভা প্রায় অনুলিপি করেছে, চেক করা ব্যতিক্রম যোগ করেনি ।
চেক করা এবং আনচেক করা ব্যতিক্রমগুলির মধ্যে প্রধান পার্থক্য কী ?
চেক করা ব্যতিক্রমগুলিতে আরোপিত অতিরিক্ত প্রয়োজনীয়তা রয়েছে । মোটামুটিভাবে বলতে গেলে, এগুলি হল:
প্রয়োজনীয়তা 1
যদি একটি পদ্ধতি একটি চেক করা ব্যতিক্রম নিক্ষেপ করে , তবে এটি অবশ্যই তার স্বাক্ষরে ব্যতিক্রমের ধরণ নির্দেশ করবে । এইভাবে, প্রতিটি পদ্ধতি যা এটিকে কল করে তা সচেতন যে এটিতে এই "অর্থপূর্ণ ব্যতিক্রম" ঘটতে পারে।
কীওয়ার্ডের পরে মেথড প্যারামিটারের পরে চেক করা ব্যতিক্রমগুলি নির্দেশ করুন ( ভুল করে কীওয়ার্ডটি ব্যবহার করবেন না )। এটা এই মত কিছু দেখায়:throws
throw
type method (parameters) throws exception
উদাহরণ:
চেক করা ব্যতিক্রম | অচেক ব্যতিক্রম |
---|---|
|
|
ডানদিকের উদাহরণে, আমাদের কোড একটি অচেক করা ব্যতিক্রম ছুঁড়ে দেয় — কোনো অতিরিক্ত পদক্ষেপের প্রয়োজন নেই। বাম দিকের উদাহরণে, পদ্ধতিটি একটি চেক করা ব্যতিক্রম ছুঁড়ে দেয়, তাই throws
ব্যতিক্রমের প্রকারের সাথে মেথড সিগনেচারে কীওয়ার্ড যোগ করা হয়।
যদি একটি পদ্ধতি একাধিক চেক করা ব্যতিক্রমগুলি ছুঁড়ে দেওয়ার আশা করে , তবে সেগুলিকে অবশ্যই throws
কমা দ্বারা পৃথক করে কীওয়ার্ডের পরে নির্দিষ্ট করতে হবে। আদেশ গুরুত্বপূর্ণ নয়. উদাহরণ:
public void calculate(int n) throws Exception, IOException
{
if (n == 0)
throw new Exception("n is null!");
if (n == 1)
throw new IOException("n is 1");
}
প্রয়োজনীয়তা 2
আপনি যদি এমন একটি পদ্ধতিকে কল করেন যা তার স্বাক্ষরে ব্যতিক্রমগুলি চেক করেছে, আপনি এই বিষয়টিকে উপেক্ষা করতে পারবেন না যে এটি তাদের নিক্ষেপ করে।
catch
আপনাকে হয় প্রতিটির জন্য ব্লক যোগ করে অথবা আপনার পদ্ধতির জন্য একটি throws
ধারা যোগ করে এই ধরনের সব ব্যতিক্রম ধরতে হবে ।
এটা যেন আমরা বলছি, " এই ব্যতিক্রমগুলি এতই গুরুত্বপূর্ণ যে আমাদের অবশ্যই সেগুলি ধরতে হবে৷ এবং যদি আমরা জানি না কীভাবে সেগুলি পরিচালনা করতে হয়, তবে যে কেউ আমাদের পদ্ধতিকে কল করতে পারে তাকে অবশ্যই অবহিত করা উচিত যে এই জাতীয় ব্যতিক্রমগুলি এতে ঘটতে পারে৷
উদাহরণ:
কল্পনা করুন যে আমরা মানুষের দ্বারা জনবহুল একটি পৃথিবী তৈরি করার জন্য একটি পদ্ধতি লিখছি। লোকের প্রাথমিক সংখ্যা একটি যুক্তি হিসাবে পাস করা হয়. তাই খুব কম লোক থাকলে আমাদের ব্যতিক্রম যোগ করতে হবে।
পৃথিবী সৃষ্টি করা | বিঃদ্রঃ |
---|---|
|
পদ্ধতিটি সম্ভাব্যভাবে দুটি চেক করা ব্যতিক্রম নিক্ষেপ করে:
|
এই পদ্ধতি কল 3 উপায়ে পরিচালনা করা যেতে পারে:
1. কোনো ব্যতিক্রম ধরবেন না
এটি প্রায়শই করা হয় যখন পদ্ধতিটি সঠিকভাবে পরিস্থিতি পরিচালনা করতে জানে না।
কোড | বিঃদ্রঃ |
---|---|
|
কলিং পদ্ধতি ব্যতিক্রমগুলি ধরতে পারে না এবং সেগুলি সম্পর্কে অন্যদের জানাতে হবে: এটি তাদের নিজস্ব ধারায় যুক্ত throws করে |
2. কিছু ব্যতিক্রম ধরুন
আমরা যে ত্রুটিগুলি পরিচালনা করতে পারি তা হ্যান্ডেল করি। কিন্তু আমরা যেগুলি বুঝতে পারি না, আমরা তাদের কলিং পদ্ধতিতে ফেলে দিই। এটি করার জন্য, আমাদের থ্রোস ক্লজে তাদের নাম যুক্ত করতে হবে:
কোড | বিঃদ্রঃ |
---|---|
|
কলকারী শুধুমাত্র একটি চেক করা ব্যতিক্রম ক্যাচ করে — LonelyWorldException । অন্য ব্যতিক্রমটি অবশ্যই তার স্বাক্ষরে যোগ করতে হবে, এটি throws কীওয়ার্ডের পরে নির্দেশ করে |
3. সব ব্যতিক্রম ধরুন
যদি পদ্ধতিটি কলিং পদ্ধতিতে ব্যতিক্রম না ফেলে, তবে কলিং পদ্ধতিটি সর্বদা আত্মবিশ্বাসী যে সবকিছু ঠিকঠাক কাজ করেছে। এবং এটি একটি ব্যতিক্রমী পরিস্থিতি ঠিক করার জন্য কোন পদক্ষেপ নিতে অক্ষম হবে।
কোড | বিঃদ্রঃ |
---|---|
|
সব ব্যতিক্রম এই পদ্ধতিতে ধরা হয়। কলকারী আত্মবিশ্বাসী হবে যে সবকিছু ঠিকঠাক হয়েছে। |
3. মোড়ানো ব্যতিক্রম
চেক করা ব্যতিক্রমগুলি তাত্ত্বিকভাবে দুর্দান্ত বলে মনে হয়েছিল, তবে অনুশীলনে এটি একটি বিশাল হতাশা হিসাবে পরিণত হয়েছিল।
ধরুন আপনার প্রজেক্টে একটি সুপার পপুলার মেথড আছে। এটি আপনার প্রোগ্রামের শত শত জায়গা থেকে কল করা হয়. এবং আপনি এটিতে একটি নতুন চেক করা ব্যতিক্রম যোগ করার সিদ্ধান্ত নেন । এবং এটি ভাল হতে পারে যে এই চেক করা ব্যতিক্রমটি সত্যিই গুরুত্বপূর্ণ এবং এতটাই বিশেষ যে শুধুমাত্র main()
পদ্ধতিটি জানে যে এটি ধরা পড়লে কী করতে হবে।
এর মানে আপনাকে আপনার সুপার জনপ্রিয় পদ্ধতি কল করে এমন প্রতিটি পদ্ধতির ধারায় চেক করা ব্যতিক্রম যোগthrows
করতে হবে । সেইসাথে ক্লজে throws
সব মেথডকে সেই মেথড বলে। এবং যে পদ্ধতিগুলিকে সেই পদ্ধতিগুলি বলে।
ফলস্বরূপ, throws
প্রকল্পের অর্ধেক পদ্ধতির ধারাগুলি একটি নতুন চেক করা ব্যতিক্রম পায়। এবং অবশ্যই আপনার প্রকল্প পরীক্ষা দ্বারা আচ্ছাদিত, এবং এখন পরীক্ষা কম্পাইল না. এবং এখন আপনাকে আপনার পরীক্ষাগুলিতেও থ্রো ক্লজগুলি সম্পাদনা করতে হবে।
এবং তারপরে আপনার সমস্ত কোড (শত শত ফাইলের সমস্ত পরিবর্তন) অন্যান্য প্রোগ্রামারদের দ্বারা পর্যালোচনা করতে হবে। এবং এই মুহুর্তে আমরা নিজেদেরকে প্রশ্ন করি কেন আমরা প্রকল্পে এত রক্তাক্ত পরিবর্তন করেছি? কাজের দিন(গুলি?) এবং ভাঙা পরীক্ষা - সবই একটি চেক করা ব্যতিক্রম যোগ করার জন্য ?
এবং অবশ্যই, উত্তরাধিকার এবং পদ্ধতি ওভাররাইডিং সম্পর্কিত সমস্যা এখনও রয়েছে। চেক করা ব্যতিক্রম থেকে আসা সমস্যাগুলি সুবিধার চেয়ে অনেক বড়। নীচের লাইন হল যে এখন খুব কম লোকই তাদের ভালবাসে এবং খুব কম লোকই তাদের ব্যবহার করে।
তবে এখনও অনেক কোড রয়েছে (স্ট্যান্ডার্ড জাভা লাইব্রেরি কোড সহ) যাতে এই চেক করা ব্যতিক্রমগুলি রয়েছে। তাদের সাথে কি করা উচিত? আমরা তাদের উপেক্ষা করতে পারি না, এবং আমরা তাদের পরিচালনা করতে জানি না।
জাভা প্রোগ্রামাররা চেক করা ব্যতিক্রমগুলিকে মোড়ানোর প্রস্তাব করেছে RuntimeException
। অন্য কথায়, সমস্ত চেক করা ব্যতিক্রমগুলি ধরুন এবং তারপরে চেক না করা ব্যতিক্রমগুলি তৈরি করুন (উদাহরণস্বরূপ, RuntimeException
) এবং পরিবর্তে তাদের ফেলে দিন। এটি করার মত কিছু দেখায়:
try
{
// Code where a checked exception might occur
}
catch(Exception exp)
{
throw new RuntimeException(exp);
}
এটি একটি খুব সুন্দর সমাধান নয়, তবে এখানে অপরাধী বলে কিছু নেই: ব্যতিক্রমটি কেবল একটি এর ভিতরে স্টাফ করা হয়েছিল RuntimeException
।
যদি ইচ্ছা হয়, আপনি সহজেই সেখান থেকে এটি পুনরুদ্ধার করতে পারেন। উদাহরণ:
কোড | বিঃদ্রঃ |
---|---|
|
অবজেক্টের ভিতরে সংরক্ষিত ব্যতিক্রম পান RuntimeException । ভেরিয়েবলটি এর ধরন নির্ধারণ করতে cause পারে null এবং এটিকে চেক করা ব্যতিক্রম টাইপে রূপান্তর করতে পারে। |
4. একাধিক ব্যতিক্রম ধরা
প্রোগ্রামাররা কোড নকল করতে সত্যিই ঘৃণা করে। এমনকি তারা একটি সংশ্লিষ্ট উন্নয়ন নীতি নিয়ে এসেছিল: নিজেকে পুনরাবৃত্তি করবেন না (DRY) । কিন্তু ব্যতিক্রমগুলি পরিচালনা করার সময়, প্রায়শই এমন ঘটনা ঘটে যখন একটি try
ব্লকের পরে catch
একই কোড সহ একাধিক ব্লক থাকে।
catch
অথবা একই কোড সহ 3টি ব্লক এবং catch
অন্যান্য অভিন্ন কোড সহ আরও 2টি ব্লক থাকতে পারে । এটি একটি আদর্শ পরিস্থিতি যখন আপনার প্রকল্প দায়িত্বশীলভাবে ব্যতিক্রমগুলি পরিচালনা করে।
সংস্করণ 7 থেকে শুরু করে, জাভা ভাষায় একটি একক catch
ব্লকে একাধিক ধরণের ব্যতিক্রম নির্দিষ্ট করার ক্ষমতা যুক্ত করেছে। এটা এই মত কিছু দেখায়:
try
{
// Code where an exception might occur
}
catch (ExceptionType1 | ExceptionType2 | ExceptionType3 name)
{
// Exception handling code
}
catch
আপনি যতটা চান ব্লক রাখতে পারেন । যাইহোক, একটি একক catch
ব্লক ব্যতিক্রমগুলি নির্দিষ্ট করতে পারে না যা একে অপরের উত্তরাধিকারী হয়। অন্য কথায়, আপনি ক্যাচ ( Exception
| RuntimeException
ই) লিখতে পারবেন না, কারণ RuntimeException
ক্লাসটি উত্তরাধিকারসূত্রে পায় Exception
।
5. কাস্টম ব্যতিক্রম
আপনি সবসময় আপনার নিজস্ব ব্যতিক্রম ক্লাস তৈরি করতে পারেন। আপনি কেবল একটি ক্লাস তৈরি করুন যা RuntimeException
ক্লাসের উত্তরাধিকারী হয়। এটি এই মত কিছু দেখাবে:
class ClassName extends RuntimeException
{
}
আপনি যখন OOP, উত্তরাধিকার, কনস্ট্রাক্টর এবং পদ্ধতি ওভাররাইডিং শিখবেন তখন আমরা বিস্তারিত আলোচনা করব।
যাইহোক, এমনকি যদি আপনার শুধুমাত্র এই মত একটি সাধারণ ক্লাস থাকে (সম্পূর্ণ কোড ছাড়া), আপনি এখনও এটির উপর ভিত্তি করে ব্যতিক্রমগুলি নিক্ষেপ করতে পারেন:
কোড | বিঃদ্রঃ |
---|---|
|
একটি আনচেক নিক্ষেপ MyException . |
জাভা মাল্টিথ্রেডিং কোয়েস্টে , আমরা আমাদের নিজস্ব কাস্টম ব্যতিক্রমগুলির সাথে কাজ করার জন্য গভীরভাবে ডুব দেব।
GO TO FULL VERSION