"মেমরির জন্য ভয়ঙ্কর" যুক্তিটি সম্পূর্ণ ভুল, তবে এটি একটি উদ্দেশ্যমূলক "খারাপ অভ্যাস"। আপনি যখন কোনও শ্রেণি থেকে উত্তরাধিকারী হন, আপনি কেবল সেই ক্ষেত্র এবং পদ্ধতিগুলির বিষয়ে উত্তীর্ণ হন না যা তার পক্ষে আগ্রহী Instead পরিবর্তে, আপনি সমস্ত কিছুর উত্তরাধিকারী হন । প্রতিটি পদ্ধতি যা এটি ঘোষণা করে, এটি আপনার পক্ষে কার্যকর না হলেও। এবং সর্বাধিক গুরুত্বপূর্ণ, আপনি এর সমস্ত চুক্তিও পেয়েছেন এবং ক্লাসটি সরবরাহ করে তার গ্যারান্টি দেয়।
সংক্ষিপ্ত আকার SOLID ভাল বস্তু-ভিত্তিক নকশার জন্য কিছু হিউরিস্টিক্স সরবরাহ করে। এখানে, আই নটারফেস বিভাজন নীতি (আইএসপি) এবং এল ইসকোভ সাবস্টিটিউশন প্রিসিনপল (এলএসপি) এর কিছু বলার আছে।
আইএসপি আমাদের ইন্টারফেসগুলি যতটা সম্ভব ছোট রাখতে বলে। তবে উত্তরাধিকার সূত্রে ArrayList
আপনি অনেকগুলি এবং অনেক পদ্ধতি পান। এটা অর্থপূর্ণ হয় get()
, remove()
, set()
(প্রতিস্থাপন), অথবা add()
একটি নির্দিষ্ট সূচিতে (সন্নিবেশ) একটি শিশু নোড? ensureCapacity()
অন্তর্নিহিত তালিকার পক্ষে এটি বোধগম্য ? এটি sort()
নোডের অর্থ কী ? আপনার শ্রেণীর ব্যবহারকারীদের কি আসলেই একটি পাওয়ার কথা subList()
? যেহেতু আপনি চান না এমন পদ্ধতিগুলি আপনি গোপন করতে পারবেন না, কেবলমাত্র সমাধান হ'ল অ্যারেলিস্টকে সদস্য ভেরিয়েবল হিসাবে রাখা, এবং আপনি যে পদ্ধতিগুলি চান প্রকৃতপক্ষে ফরোয়ার্ড করুন:
private final ArrayList<Node> children = new ArrayList();
public void add(Node child) { children.add(child); }
public Iterator<Node> iterator() { return children.iterator(); }
ডকুমেন্টেশনে আপনি যে সমস্ত পদ্ধতি দেখেন তা যদি আপনি সত্যিই চান তবে আমরা এলএসপিতে যেতে পারি। এলএসপি আমাদের জানায় যে প্যারেন্ট ক্লাসটি যেখানেই আশা করা হচ্ছে সেখানে অবশ্যই আমাদের সাবক্লাস ব্যবহার করতে সক্ষম হব। যদি কোনও ফাংশন একটি ArrayList
প্যারামিটার হিসাবে নেয় এবং আমরা Node
তার পরিবর্তে আমাদের পাস করি তবে কিছুই পরিবর্তন হওয়ার কথা নয়।
সাবক্লাসগুলির সামঞ্জস্যতা প্রকার স্বাক্ষরের মতো সাধারণ জিনিস দিয়ে শুরু হয়। আপনি যখন কোনও পদ্ধতিকে ওভাররাইড করেন, আপনি প্যারামিটারের ধরণগুলিকে আরও কঠোর করতে পারবেন না কারণ এটি প্যারেন্ট ক্লাসের সাথে আইনী ব্যবহারগুলি বাদ দিতে পারে। তবে এটি জাভাতে সংকলক আমাদের জন্য যাচাই করে।
তবে এলএসপি আরও গভীরভাবে চলে: আমাদের প্যারেন্ট ক্লাস এবং ইন্টারফেসের ডকুমেন্টেশন দ্বারা প্রতিশ্রুতিবদ্ধ সমস্ত কিছুর সাথে আমাদের সামঞ্জস্যতা বজায় রাখতে হবে। ইন তাদের উত্তর , লিন এক ধরনের ক্ষেত্রে যেখানে পাওয়া গেছে List
ইন্টারফেস (আপনি মাধ্যমে উত্তরাধিকারসূত্রে যা ArrayList
) গ্যারান্টী বা নিশ্চয়তা দিচ্ছে কিভাবে equals()
এবং hashCode()
পদ্ধতি কাজ অনুমিত হয়। জন্য hashCode()
আপনি এমনকি একটি নির্দিষ্ট অ্যালগরিদম যে ঠিক প্রয়োগ করা আবশ্যক দেওয়া হয়। ধরে নেওয়া যাক আপনি এটি লিখেছেন Node
:
public class Node extends ArrayList<Node> {
public final int value;
public Node(int value, Node... children) {
this.value = Value;
for (Node child : children)
add(child);
}
...
}
এটির প্রয়োজন এটি কার্যকর করতে value
পারে না hashCode()
এবং প্রভাব ফেলতে পারে না equals()
। List
ইন্টারফেস - যা আপনি এটা থেকে inheriting দ্বারা সম্মান অঙ্গীকার - প্রয়োজন new Node(0).equals(new Node(123))
সত্য হতে পারে।
যেহেতু ক্লাসগুলি থেকে উত্তরাধিকার সূচিত হওয়া দুর্ঘটনাক্রমে একটি পিতামাত্ত শ্রেণীর করা একটি প্রতিশ্রুতি ভঙ্গ করা খুব সহজ করে তোলে এবং এটি সাধারণত আপনার ইচ্ছা থেকে আরও বেশি পদ্ধতি উদ্ঘাটন করে, তাই সাধারণত পরামর্শ দেওয়া হয় যে আপনি উত্তরাধিকারের চেয়ে রচনা পছন্দ করেন । আপনার যদি কিছু উত্তরাধিকার সূত্রে আবশ্যক হয় তবে এটি কেবল ইন্টারফেসের উত্তরাধিকার সূত্রে প্রস্তাবিত। আপনি যদি কোনও নির্দিষ্ট শ্রেণীর আচরণ পুনরায় ব্যবহার করতে চান, আপনি এটিকে একটি পৃথক বস্তু হিসাবে একটি উদাহরণ পরিবর্তনশীল হিসাবে রাখতে পারেন, তার সমস্ত প্রতিশ্রুতি এবং প্রয়োজনীয়তা আপনাকে বাধ্য করা হয় না।
কখনও কখনও, আমাদের প্রাকৃতিক ভাষা একটি উত্তরাধিকার সম্পর্কের পরামর্শ দেয়: গাড়ী একটি বাহন। মোটরসাইকেল একটি বাহন। আমার কি ক্লাস সংজ্ঞায়িত করা উচিত Car
এবং Motorcycle
সেই ক্লাস থেকে উত্তরাধিকারী হওয়া উচিত Vehicle
? অবজেক্ট-ওরিয়েন্টেড ডিজাইন আমাদের কোডে হুবহু রিয়েল ওয়ার্ল্ডকে আয়না দেওয়ার বিষয়ে নয়। আমরা সহজেই আমাদের উত্স কোডটিতে আসল বিশ্বের সমৃদ্ধ শ্রেণিবদ্ধগুলি এনকোড করতে পারি না।
এরকম একটি উদাহরণ হ'ল কর্মচারী-বসের মডেলিংয়ের সমস্যা। আমাদের Person
একটি নাম এবং ঠিকানা সহ একাধিক গুলি রয়েছে। একটি Employee
একটি Person
এবং এর একটি আছে Boss
। একটি Boss
একটি হল Person
। তাই আমি একটি তৈরি করা উচিত Person
বর্গ যে উত্তরাধিকারসূত্রে হয় Boss
এবং Employee
? এখন আমার একটি সমস্যা আছে: বসও একজন কর্মচারী এবং আরও একটি উচ্চতর রয়েছে। সুতরাং এটি Boss
প্রসারিত করা উচিত বলে মনে হচ্ছে Employee
। কিন্তু এটি CompanyOwner
একটি Boss
কিন্তু একটি নয় Employee
? যে কোনও ধরণের উত্তরাধিকারের গ্রাফটি এখানে কোনওভাবে ভেঙে যাবে।
ওওপি শ্রেণিবদ্ধতা, উত্তরাধিকার এবং বিদ্যমান বর্গগুলির পুনরায় ব্যবহার সম্পর্কে নয়, এটি আচরণকে সাধারণীকরণ সম্পর্কে । ওওপি সম্পর্কে "আমার কাছে প্রচুর অবজেক্ট রয়েছে এবং সেগুলি একটি বিশেষ কাজ করতে চায় - এবং কীভাবে আমি তা বিবেচনা করি না” " ইন্টারফেসের জন্য এটিই । আপনি যদি এটির Iterable
জন্য ইন্টারফেসটি কার্যকর করেন Node
কারণ আপনি এটি পুনরাবৃত্তি করতে চান, এটি পুরোপুরি ঠিক। আপনি যদি Collection
ইন্টারফেসটি প্রয়োগ করেন কারণ আপনি শিশু নোড ইত্যাদি যুক্ত করতে / সরাতে চান তবে ঠিক আছে। কিন্তু অন্য শ্রেণীর কাছ থেকে উত্তরাধিকার সূত্রে প্রাপ্ত কারণ কারণ এটি আপনাকে যা দেয় না তা সবই দেয় বা না হয় যতক্ষণ না আপনি উপরে বর্ণিত হিসাবে যত্ন সহকারে চিন্তাভাবনা না করে থাকেন।