পর্যবেক্ষক নিদর্শন; কী * পরিবর্তন হয়েছে জেনে?


10

আমি দুটি অ্যাবস্ট্রাক্ট ক্লাস সাবজেক্ট এবং অবজারভার তৈরি করেছি যা ক্লাসিক অবজারভার প্যাটার্ন ইন্টারফেসকে সংজ্ঞায়িত করে। আমি পর্যবেক্ষক প্যাটার্নটি বাস্তবায়নের জন্য তাদের কাছ থেকে পেয়েছি। কোনও পর্যবেক্ষক এর মতো দেখতে পাবেন:

void MyClass::Update(Subject *subject)
{
    if(subject == myService_)
    {
        DoSomething();
    }
    else if(subject == myOtherService_)
    {
        DoSomethingElse();
    }
}

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

আমার ক্ষেত্রে আমার জানতে হবে যে বিষয়টি নিয়ে দু'একটি ভিন্ন ক্রিয়াকলাপ ঘটেছে এবং যদি এটি কোনও নির্দিষ্ট ক্রিয়া হয় তবে সেই ক্রিয়া সম্পর্কিত কোনও পূর্ণসংখ্যার সংখ্যাটি জানতে হবে।

সুতরাং আমার প্রশ্নগুলি হ'ল:

  1. জেনেরিক আর্গুমেন্ট (জাভা যেমন করে) পাস করার সি ++ উপায় কী?
  2. পর্যবেক্ষক এমনকি সেরা প্যাটার্ন? সম্ভবত কোন ধরণের ইভেন্ট সিস্টেম?

হালনাগাদ

আমি এই নিবন্ধটি পেয়েছি যা পর্যবেক্ষক প্যাটার্নকে টেম্পলেট করার বিষয়ে আলোচনা করে: টেমপ্লেটগুলি সহ একটি বিষয় / পর্যবেক্ষক নিদর্শন বাস্তবায়ন করে । এটি আমাকে বিস্মিত করেছে যে আপনি কোনও যুক্তি টেম্পলেট করতে পারেন কিনা।

আমি এই স্ট্যাক ওভারফ্লো প্রশ্নটি পেয়েছি যা আর্গুমেন্টকে টেম্পলেট করার বিষয়ে কথা বলে: টেমপ্লেট ভিত্তিক সাবজেক্ট পর্যবেক্ষক প্যাটার্ন - আমাকে স্ট্যাটিক_কাস্ট বা ডায়নামিক_কাস্ট ব্যবহার করা উচিত ? তবে ওপিতে মনে হচ্ছে এমন কোনও সমস্যা আছে যার উত্তর কেউ দেয়নি।

অন্য যে জিনিসটি আমি করতে পারি তা হ'ল ইভেন্ট পদ্ধতিটি অবজেক্ট হিসাবে নেওয়ার জন্য আপডেট পদ্ধতিটি পরিবর্তন করুন:

void MyClass::Update(Subject *subject, EventArg arg)
{
  ...

এবং তারপরে নির্দিষ্ট আর্গুমেন্ট ডেটার জন্য ইভেন্টআর্গের সাবক্লাসগুলি তৈরি করুন এবং তারপরে আমি অনুমান করি যে এটি আপডেট পদ্ধতির মধ্যে নির্দিষ্ট সাবক্লাসে ফিরে যাবে।

আপডেট 2

এছাড়াও একটি নিবন্ধ পাওয়া গেছে, একটি অ্যাসিনক্রোনাস বার্তা-ভিত্তিক সি ++ ফ্রেমওয়ার্ক তৈরি করার সময়; অংশ ২ যা সাবজেক্টটি কী পরিবর্তন হয়েছে সে সম্পর্কে বিস্তারিত জানার বিষয়ে আলোচনা করে ।

আমি এখন Boost.Signals ব্যবহারের জন্য গুরুত্ব সহকারে বিবেচনা করছি । আমার নিজের পর্যবেক্ষক প্যাটার্নটি ব্যবহার করা যখন এটি সহজ ছিল তখন তা বোধগম্য হয়েছিল, তবে প্রকারটি এবং আর্গুমেন্টকে জটিল করে জটিল হতে শুরু করে। এবং আমার বুস্ট ডাবল সিগন্যালস 2 এর থ্রেড সুরক্ষা প্রয়োজন।

আপডেট 3

আমি পর্যবেক্ষক প্যাটার্নে কিছু আকর্ষণীয় নিবন্ধগুলিও পেয়েছি:

ভেষজ সুতার দ্বারা সাধারণ পর্যবেক্ষক

সি ++ - পার্ট 1 এ পর্যবেক্ষক প্যাটার্নটি কার্যকর করা

পর্যবেক্ষক ডিজাইন প্যাটার্ন বাস্তবায়নের অভিজ্ঞতা (অংশ 2)

পর্যবেক্ষক নকশা প্যাটার্ন বাস্তবায়নের অভিজ্ঞতা (অংশ 3)

যাইহোক, আমি বুস্ট.সিনগালস ব্যবহার করে আমার বাস্তবায়নটি পরিবর্তন করেছি যা সম্ভবত আমার পক্ষে আমার উদ্দেশ্যে স্ফোটিত হয়েছে, সফলভাবে কাজ করছে। এবং সম্ভবত ফোলা বা গতির কোনও উদ্বেগ অপ্রাসঙ্গিক।


শরীরের প্রশ্নগুলি সত্যিই আপনার শিরোনামের সাথে মেলে না। আসলেই মূল প্রশ্নটি কোনটি?
নিকোল

@ রেনেসিস: আমি বর্তমানে আমার পোস্টের শুরুতে কোড নমুনার মতো পর্যবেক্ষক প্যাটার্নটি ব্যবহার করছি। আমি বর্তমানে যে কোডটিতে কাজ করছি তার জন্য, এটি সক্রিয় হয়ে গেছে যে আমি কীভাবে পরিবর্তন করেছি তা নির্দিষ্টভাবে জানতে হবে যাতে আমি সে অনুযায়ী প্রতিক্রিয়া জানাতে পারি। আমার পর্যবেক্ষক প্যাটার্নের বর্তমান বাস্তবায়ন (যা আদর্শ এক) এই তথ্য সরবরাহ করে না। আমার প্রশ্ন হ'ল কী পরিবর্তন হয়েছে সে সম্পর্কে কীভাবে সেরা তথ্য পাবেন।
ব্যবহারকারী

@ রেনেসিস: এখানে আমার কাছে অনুরূপ প্রশ্ন জিজ্ঞাসা করা ফোরামের থ্রেড: গেমদেব.ট.
ব্যবহারকারী-

বিজ্ঞাপন আপডেট 2: আমি অবশ্যই বুস্ট.সাইনাল ব্যবহার করে সমর্থন করি। এটি নিজের রোলিংয়ের চেয়ে অনেক বেশি সুবিধাজনক। রয়েছে libsigc ++, যদি আপনি শুধু এই কাজের (Boost.Signals বুস্ট বাকি থেকে কোড অনেক ব্যবহার করে) জন্য কিছু লাইটার-ওজন চেয়েছিলেন; যদিও এটি থ্রেড-নিরাপদ নয়।
জানু হুডেক

গতির সমস্যাগুলি সম্পর্কে: আমি স্পষ্টভাবে জানি না যে কতটা দ্রুত বুস্ট ign সিগন্যালগুলি হয়, তবে এটি কেবল তখনই উদ্বেগ যখন আপনার চারপাশে প্রচুর পরিমাণে ইভেন্টগুলি উড়িত হয় ...
সর্বোচ্চ

উত্তর:


4

কিনা সি ++ বা জাভা, পর্যবেক্ষক একটি বিজ্ঞপ্তি পারেন এর তথ্য দিয়ে বরাবর আসা কি পরিবর্তিত হয়। একই পদ্ধতিগুলি notifyObservers (অবজেক্ট আর্গ) এছাড়াও সি ++ তেও ব্যবহার করা যেতে পারে।

সাধারণত, বিষয়টি থেকে যাবে যে এক বা একাধিক পর্যবেক্ষকের কাছে একাধিক বিষয় প্রেরণ করা হতে পারে এবং তাই, এগুলি class argহার্ড কোডিং করা যায় না।

সাধারণত, করানোর সর্বোত্তম উপায় হ'ল জেনেরিক বার্তা / টোকেন আকারে আর্গুমেন্ট করা যা বিভিন্ন শ্রেণীর জন্য একই ডেটা টাইপ করে তবে বিভিন্ন পর্যবেক্ষণ করা শ্রেণীর জন্য মান পৃথক হয়। বিকল্পভাবে, যদি এই জাতীয় সমস্ত বিজ্ঞপ্তির মানগুলি কিছু ভিত্তিক শ্রেণীর উপর থেকে শ্রেণীর বাইরে নেওয়া হয় যা সকলের কাছে সাধারণ।

পর্যবেক্ষক প্যাটার্ন জন্য, এটি হল গুরুত্বপূর্ণ Arg ডাটা টাইপ হার্ড observee এবং পর্যবেক্ষক মধ্যে কোডেড না - অন্য একটি কাপলিং যে জিনিস অভিব্যক্ত কঠিন করে তোলে।

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


5
পর্যবেক্ষক যুক্তি ব্যাখ্যা করে, তাহলে হয় একটি সংযোজন, কোন ব্যাপার কিভাবে আপনি টাইপ লুকান। আসলে আমি এটা বলতে চাই আরো অভিব্যক্ত কঠিন যদি আপনি পাস Object( void *, boost::anyবা কিছু একভাবে জেনেরিক) যদি আপনি নির্দিষ্ট ধরনের, কারণ নির্দিষ্ট ধরনের আপনি কম্পাইল সময় যে কিছু পরিবর্তিত এ দেখতে পাবেন সঙ্গে, যখন জেনেরিক ধরনের সঙ্গে পাস এটা সংকলন করবে এবং কাজ করা বন্ধ করবে, কারণ পর্যবেক্ষক উত্তীর্ণ প্রকৃত ডেটা দিয়ে কাজ করতে সক্ষম হবে না।
জানু হুডেক

@ জানহুদেক: আমি এর সাথে একমত, তবে তার অর্থ কি আপনি প্রতিটি যুক্তির জন্য (যেমন, প্রতিটি ব্যবহারের ক্ষেত্রে) একটি নির্দিষ্ট এক-অফ পর্যবেক্ষক / সাবজেক্ট সাবক্লাস সেট করেন?
ব্যবহারকারী

@ জানহুদেক: মিলনও একটাই পথ। বিষয়টি পর্যবেক্ষকদের সম্পর্কে কোনও ধারণা নেই। হ্যাঁ পর্যবেক্ষক বিষয়টি সম্পর্কে জানেন তবে পর্যবেক্ষকরা যেভাবে কাজ করেন তা নয়?
ব্যবহারকারী

1
@ ব্যবহারকারী: হ্যাঁ, আমি প্রতিটি বিষয়ের জন্য একটি নির্দিষ্ট ইন্টারফেস তৈরি করি এবং প্রতিটি পর্যবেক্ষক এটি পর্যবেক্ষণের জন্য প্রয়োজনীয় বিষয়গুলির ইন্টারফেসগুলি প্রয়োগ করে। ঠিক আছে, আমি যে সমস্ত ভাষা ব্যবহার করি সেগুলির ভাষা বা কাঠামোয় আবদ্ধ পদ্ধতি পয়েন্টার রয়েছে (সি # প্রতিনিধি, সি ++ 11 std::functionবুস্ট boost::function, জিটিকি + GClosure, পাইথন বাউন্ড পদ্ধতিগুলি), তাই আমি কেবল উপযুক্ত স্বাক্ষর সহ পদ্ধতিগুলি সংজ্ঞায়িত করি এবং সিস্টেমটিকে আসল তৈরি করতে বলি পর্যবেক্ষক। মিলনটি সত্যই একটি উপায়, বিষয়টি পর্যবেক্ষকদের জন্য ইন্টারফেসটি সংজ্ঞায়িত করে, তবে তাদের বাস্তবায়ন সম্পর্কে ধারণা নেই।
জানু হুডেক

0

সি ++ তে "জাভা লাইক" জেনেরিক ইভেন্টের যুক্তি প্রেরণের কয়েকটি উপায় রয়েছে।

1) ইভেন্টের যুক্তিটি অকার্যকর * হিসাবে ঘোষণা করুন এবং ইভেন্ট হ্যান্ডলারে সঠিক শ্রেণিতে ফেলে দিন।

২) ইভেন্টের যুক্তিটিকে একটি নতুন শ্রেণি / ইন্টারফেসের পয়েন্টার / রেফারির মতো ঘোষণা করুন (যেমন আপনার উদাহরণের প্রতিক্রিয়া হিসাবে)

class GenericEventArgument
{
  virtual bool didAction1Happen() = 0;
  virtual int getActionInteger() = 0;
};

এবং প্রকৃত ইভেন্ট আর্গুমেন্ট ক্লাসগুলি এই বর্গ থেকে নেওয়া হয়েছে।

আপনি যেমন কোনও টেম্পলেট ভিত্তিক পর্যবেক্ষক চেক আউট সম্পর্কিত প্রশ্ন question

http://www.codeproject.com/Articles/3267/Implementing-a-Subject-Observer-pattern-with-templ


-1

আমি জানি না যে এটি আধ্যাত্মিক নাম কিনা, তবে আমার পুরানো স্মলটালকের দিনগুলি থেকে "পর্যবেক্ষণ" শব্দটি মনে পড়ে যা পর্যবেক্ষণযোগ্যতে কী পরিবর্তন হয়েছে identify

এটি ইভেন্টআর্গের আপনার ধারণার মতো জটিল নয় (এবং এটি সাবক্লাসিং); এটি পর্যবেক্ষণযোগ্য থেকে পর্যবেক্ষকের কাছে কেবল একটি স্ট্রিং (এমনকি কোনও পূর্ণসংখ্যার ধ্রুবক হতে পারে) কেটে যায়।

প্লাস: কেবল দুটি সহজ পদ্ধতি রয়েছে ( update(observable)এবংupdateAspect(observable, aspect)

বিয়োগ: পর্যবেক্ষককে আরও তথ্যের জন্য পর্যবেক্ষককে জিজ্ঞাসা করতে হতে পারে (যেমন, আপনার "পূর্ণসংখ্যার সংখ্যা")

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