যদি কোনও বস্তু তার মালিকের অনেক কিছু জানে তবে এটি কি কোডের গন্ধ?


9

আমাদের ডেলফি 2007 অ্যাপ্লিকেশনটিতে আমরা নীচের অনেকগুলি নির্মাণ ব্যবহার করছি

FdmBasic:=TdmBasicData(FindOwnerClass(AOwner,TdmBasicData));

FindOwnerClass একটি নির্দিষ্ট শ্রেণি (উদাহরণস্বরূপ TdmBasicData) সন্ধানের জন্য বর্তমান উপাদানটির মালিক শ্রেণিবিন্যাস উপরের দিকে ভ্রমণ করে s ফলাফল অবজেক্টটি ফিল্ড ভেরিয়েবল এফডিএমবাসিকে সঞ্চিত থাকে। আমরা এটি প্রাথমিকভাবে পাশাপাশি ডেটামোডুলগুলি পাস করতে ব্যবহার করি।

উদাহরণ: প্রতিবেদন তৈরি করার সময়, ফলস্বরূপ ডেটাডমডুল টিডিএমরপোর্টবেসডাটা দ্বারা অ্যাক্সেস করা একটি টেবিলের একটি ব্লব ক্ষেত্রটিতে ফলাফলগুলি সংকুচিত করা হয় এবং সংরক্ষণ করা হয়। আমাদের অ্যাপ্লিকেশনটির একটি পৃথক মডিউলে, রিপোর্টবিল্ডার ব্যবহার করে পেজড ফর্মে রিপোর্ট থেকে ডেটা দেখানোর কার্যকারিতা রয়েছে। এই মডিউলটির প্রধান কোড (টিডিএমআরবিআরপোর্ট), সংবেদনশীল ব্লব ডেটা বিভিন্ন টেবিলগুলিতে রূপান্তর করতে একটি ক্লাস টিআরবিটেম্পাটাবেস ব্যবহার করে যা রিপোর্ট বিল্ডার রানটাইম রিপোর্ট ডিজাইনার-এ ব্যবহারযোগ্য। টিডিএমআরবিআরপোর্টে প্রতিবেদন সম্পর্কিত সমস্ত ধরণের ডেটা (রিপোর্টের ধরণ, রিপোর্টের গণনার মান নির্ধারণ ইত্যাদি) এর জন্য টিডিএমআরপোর্টব্যাসডেটার অ্যাক্সেস রয়েছে। টিআরবিটিম্পডাটাবেস টিডিএমআরবিআরপোর্টে নির্মিত তবে টিডিএমরেপ্টবারেসেটা অ্যাক্সেস করতে হবে। সুতরাং এটি এখন উপরের নির্মাণ ব্যবহার করে করা হয়েছে:

constructor TRBTempDatabase.Create(aOwner: TComponent);
begin
  inherited Create(aOwner);

  FdmReportBaseData := TdmRBReport(FindOwnerClass(Owner, TdmRBReport)).dmReportBaseData;
end;{- .Create }

আমার অনুভূতি হ'ল এর অর্থ এই যে টিআরবিটিম্পডাটাবেস তার মালিককে অনেক কিছু জানে এবং আমি ভাবছিলাম যে এটি কোনওরকম কোডের গন্ধ বা অ্যান্টি-প্যাটার্ন।

এই সম্পর্কে আপনি কি বলবেন? এটি কি কোডের গন্ধ? যদি তা হয় তবে এর থেকে উত্তম উপায় কী?


1
যদি এটি অন্য ক্লাস সম্পর্কে অনেক কিছু জানার কথা ছিল তবে এটি করার সহজ উপায় সরবরাহ করা হত।
লরেন পেচটেল 6'12

উত্তর:


13

এই ধরণের দেখতে কোনও সার্ভিস লোকেটার প্যাটার্নের মতো লাগে যা প্রথমে মার্টিন ফোলার দ্বারা বর্ণিত হয়েছিল (যা সাধারণ অ্যান্টি-প্যাটার্ন হিসাবে চিহ্নিত হয়েছে)।

নির্মাণ ভিত্তিক নির্ভরতা ইনজেকশনটিকে সার্ভিস লোকেটারের চেয়ে বেশি পছন্দ করা হয় কারণ এটি প্রয়োজনীয় পরামিতিগুলির দৃশ্যমানতা প্রচার করে এবং সহজ ইউনিট পরীক্ষার প্রচার করে।

সার্ভিস লোকেটার ব্যবহারে সমস্যাটি এমন নয় যে আপনি কোনও নির্দিষ্ট সার্ভিস লোকেটার প্রয়োগের উপর নির্ভরতা নিচ্ছেন (যদিও এটি সমস্যাও হতে পারে), তবে এটি একটি উদ্দীপনাবিরোধী প্যাটার্ন। এটি আপনার এপিআই-এর গ্রাহকদের একটি ভয়াবহ বিকাশকারী অভিজ্ঞতা দেবে এবং এটি আপনার রক্ষণাবেক্ষণ বিকাশকারী হিসাবে আরও খারাপ করে দেবে কারণ আপনার করা প্রতিটি পরিবর্তনের প্রভাব বোঝার জন্য আপনাকে যথেষ্ট পরিমাণে মস্তিষ্ক শক্তি ব্যবহার করতে হবে।

সংস্থাপকটি কনস্ট্রাক্টর ইঞ্জেকশন ব্যবহার করার সময় ভোক্তা এবং প্রযোজক উভয়কেই এতটা সহায়তা দিতে পারে, তবে পরিষেবা সহায়তার উপর নির্ভর করে এমন এপিআইয়ের জন্য সেই সহায়তার কোনওটিই পাওয়া যায় না।

এছাড়াও উল্লেখযোগ্যভাবে এটি ডেমিটারের আইনও ভেঙে দেয়

ল অব অফ ডিমিটার (এলওডি) বা নূন্যতম জ্ঞানের মূলসূত্র হ'ল সফটওয়্যার, বিশেষত অবজেক্ট-ওরিয়েন্টেড প্রোগ্রামগুলি বিকাশের জন্য একটি নকশার গাইডলাইন। এর সাধারণ আকারে, এলওডি হ'ল আলগা সংযোগের একটি নির্দিষ্ট ক্ষেত্রে।

ফাংশনগুলির জন্য ডেমিটারের আইনটির জন্য আবশ্যক যে কোনও বস্তুর হে এম এর একটি পদ্ধতি এম কেবলমাত্র নিম্নলিখিত ধরণের অবজেক্টগুলির পদ্ধতি আহ্বান করতে পারে:

  1. ও নিজেই
  2. এম এর পরামিতি
  3. এম এর মধ্যে যে কোনও বস্তু তৈরি / তাত্ক্ষণিক
  4. ও এর সরাসরি উপাদান উপাদান
  5. এম এর স্কোপে বিশ্বব্যাপী পরিবর্তনশীল, ও দ্বারা অ্যাক্সেসযোগ্য

বিশেষত, কোনও অবজেক্টের অন্য কোনও পদ্ধতিতে ফিরে আসা সদস্য অবজেক্টের অনুরোধ পদ্ধতিগুলি এড়ানো উচিত। ক্ষেত্র শনাক্তকারী হিসাবে বিন্দু ব্যবহার করে এমন অনেক আধুনিক অবজেক্ট ওরিয়েন্টেড ভাষার ক্ষেত্রে, আইনটি কেবল "কেবল একটি বিন্দু ব্যবহার করুন" হিসাবে বর্ণিত হতে পারে। এটি হ'ল, অ্যাবেথোড () কোডটি আইনটি ভেঙে দেয় যেখানে a.Method () না করে। একটি সাধারণ উদাহরণ হিসাবে, যখন কেউ কুকুরের হাঁটাচলা করতে চায়, তখন কুকুরের পায়ে সরাসরি চলার আদেশ দেওয়া বোকামি হবে; পরিবর্তে কেউ কুকুরকে আদেশ দেয় এবং এটিকে তার নিজের পায়ে যত্ন নিতে দেয়।

ভাল উপায়

কার্যকরীভাবে সর্বোত্তম উপায় হ'ল ক্লাসের মধ্যে সার্ভিস লোকেটার কলটি সরিয়ে ফেলা এবং এর কনস্ট্রাক্টরের ভিতরে প্যারামিটার হিসাবে সঠিক মালিককে পাস করা। এমনকি যদি এর অর্থও হয় যে আপনার কাছে কোনও পরিষেবা শ্রেণি রয়েছে যা কোনও মালিককে দেখায় এবং তারপরে ক্লাস কনস্ট্রাক্টরের কাছে যায়

constructor TRBTempDatabase.Create(aOwner: TComponent, ownerClass: IComponent);
begin
  inherited Create(aOwner);

  FdmReportBaseData := TdmRBReport(ownerClass).dmReportBaseData;
end;{- .Create }

3
দুর্দান্ত উত্তর, এবং যে কেউ এই দুর্দান্ত উপমাটি নিয়ে এসেছেন তাদের কাছে প্রপস:As a simple example, when one wants to walk a dog, it would be folly to command the dog's legs to walk directly; instead one commands the dog and lets it take care of its own legs.
অ্যান্ডি হান্ট

3

পিতা-মাতার সম্পর্কে বাচ্চাদের জিনিসগুলি খুব বেশি জেনে রাখা একটি অসুবিধা হ'ল আপনি বাস্তবায়ন করার ধরণগুলি শেষ করেন যা (এবং বেশিরভাগ ক্ষেত্রেই) খুব শক্তভাবে মিলিত হতে পারে যা বড় নির্ভরতা মাথা ব্যথা তৈরি করে এবং প্রায়শই পরে নিরাপদে পরিবর্তন এবং রক্ষণাবেক্ষণ করা খুব কঠিন হয়ে যায় পরে.

আপনার দুটি শ্রেণি কত গভীরভাবে সংযুক্ত রয়েছে তার উপর নির্ভর করে এটি কিছুটা মনে হয় যেমন ফাউলারের বিবরণ Enর্ষা বা অনুপযুক্ত ঘনিষ্ঠতা কোডের গন্ধ স্পষ্ট।

ডেটা সহ কোনও শ্রেণি লোড করা বা পড়ার দরকার আছে বলে মনে হচ্ছে, এক্ষেত্রে আপনি সন্তানের এবং তার পিতামাতার শৃঙ্খলার মধ্যে নির্ভরতা ভাঙতে বেশ কয়েকটি বিকল্প প্যাটার্ন ব্যবহার করতে পারেন এবং মনে হচ্ছে আপনার অ্যাক্সেসের কাজটি অর্পণ করতে হবে আপনার সমস্ত কিছু করার জন্য ডেটা অ্যাক্সেসর শ্রেণিকে দায়বদ্ধ করার চেয়ে আপনার ডেটা ক্লাস।

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.