Mga pattern ng Disenyo - Isang mabilis na gabay sa pattern ng Tagamasid.

Ang pattern ng tagamasid ay isang napaka-karaniwang ginagamit na pattern. Sa katunayan, ito ay karaniwang pangkaraniwan na na-standardize sa maraming mga programming language / library. Sa Java, umiiral ang injava.util.Observer (na naalis sa Java 9). Sa Python ito kasing malapit ng apip install pattern-tagamasid. Sa C ++, kung minsan maaari nating gamitin ang boost library, mas tumpak na #include . Gayunpaman, malawak itong ginagamit sa industriya bilang isang pasadyang solusyon na ginawa. Upang magamit ito nang tama at maunawaan ang pagiging kumplikado nito, kailangan nating sumisid at tuklasin ito.

Ang pattern ng tagamasid ay inuri sa mga pattern ng disenyo ng pag-uugali. Ang mga pattern ng disenyo ng pag-uugali ay pinaka-partikular na nag-aalala sa komunikasyon sa pagitan ng mga klase / bagay. [sa pamamagitan ng paliwanag ng mga pattern ng simpleng]

Ano ang pattern ng tagamasid? Bukod sa isang monitor ng paglalakad na naglalabas ng analog telebisyon (tulad ng sa larawan). Ang layunin ng pattern ay upang tukuyin ang isang-sa-maraming relasyon na kapag ang isang bagay ay nagbabago ng estado, ang iba ay awtomatiko at maa-update. Mas tumpak, nais nitong maalaman ang tungkol sa mga kaganapan na nangyayari sa system. Hinahayaan ang mga piraso ng puzzle na magkasama sa tatlong mga hakbang.

Hakbang 1 - Mga Keyword

Ang pagtukoy ng mga keyword ay ang lihim na recipe sa seryeng ito ng mga mabilis na gabay. Ang pamamaraang ito ay nakatulong sa akin talagang maunawaan ang mga pattern ng disenyo, hardcode ang mga ito sa aking isip at naiintindihan ang mga pagkakaiba sa iba pang mga pattern ng disenyo.

  1. Paksa: Itinuturing itong tagabantay ng impormasyon, ng data o lohika ng negosyo.
  2. Magrehistro / Maglakip: Ang mga manonood ay nagrehistro sa kanilang sarili sa paksa dahil nais nilang ma-notify kung may pagbabago.
  3. Kaganapan: Ang mga kaganapan ay kumikilos bilang isang nag-trigger sa paksa tulad ng lahat ng mga tagamasid ay inaalam.
  4. Ipaalam: Depende sa pagpapatupad, ang paksa ay maaaring "itulak" ang impormasyon sa mga tagamasid, o, ang mga tagamasid ay maaaring "hilahin" kung kailangan nila ng impormasyon mula sa paksa.
  5. Update: Nai-update ng mga tagamasid ang kanilang estado nang malaya mula sa iba pang mga tagamasid subalit ang kanilang estado ay maaaring magbago depende sa naganap na kaganapan.

Hakbang 2 - Diagram

Hinahayaan ang hatiin ang disenyo na ito sa iba't ibang klase upang gawing simple ito ng kaunti.

  • Ang ConcreteObservers ay mga klase na naglalaman ng impormasyon na tiyak sa kasalukuyang pagkakataon. Ang pag-update ng function ay tinawag ng operasyon ng notify () ng paksa. Ang mga tagamasid ay nakapag-iisa nang nakapag-iisa batay sa kanilang kasalukuyang estado.
  • Ang Tagamasid ay ang klase ng magulang ng mga tagamasid ng kongkreto. Naglalaman ito ng isang paksa ng paksa. Kapag sinimulan ang isang tagamasid, ipinaparehistro / nalakip ang sarili sa paksa.
  • Ang klase ng Paksa ay may listahan o isang koleksyon ng mga tagamasid. Kapag ang isang kaganapan ay na-trigger na tinatawag na ang notify () na operasyon na kung saan ang mga loop sa pamamagitan ng lahat ng mga tagamasid sa pamamagitan ng pagtawag sa kanilang pag-update ng function.

Hakbang 3 - Code ayon sa Halimbawa

Iminumungkahi kong kopyahin ang klase ng code sa klase mula sa aking gitnang repositibong "Andreas Poyias" o ang mga snippet sa ibaba (sa pagkakasunud-sunod na ibinigay) at i-paste ito sa alinman sa magagamit na mga editor ng C ++ tulad ng c ++ shell, jdoodle, onlineGDB at tumakbo upang obserbahan ang output. Pagkatapos basahin ang mga komento o paglalarawan sa ibaba. Dalhin ang iyong oras, basahin ito nang lubusan (nangangahulugan ito ng isang minuto, hindi mas mababa at hindi higit pa).

Halimbawa: Isaalang-alang ang isang laro ng football. Maraming mga tagasuporta ang nanonood ng laro. Hinahati namin ang mga tagasuporta sa dalawang kategorya ayon sa edad, bata at matanda. Kapag ang kanilang koponan ay nagmarka ng isang layunin na naiiba ang reaksyon ng mga tagasuporta ayon sa kanilang edad at antas ng kanilang kaguluhan.
Ngayon, makipag-usap tayo sa mga term na ginamit para sa pattern ng tagamasid:

  • Ang laro ay ang paksa at ang mga tagasuporta ay ang mga tagamasid.
  • Ang lahat ng mga nagmamasid ay nakakabit / nakarehistro sa paksa at inaalam sila kapag ang kanilang mga koponan sa football ng koponan (ang trigger-event ay kung ang kanilang mga marka ng koponan).
  • Ina-update ng mga tagamasid ang kanilang pag-uugali depende sa natanggap na abiso.

Paksa
Para sa klase na ito, kailangan namin ng pag-access sa isang listahan ng mga tagamasid. Kapag malapit nang magparehistro ang mga nagmamasid, tinawag nila ang function naattatt (ito) upang idagdag ang kanilang sarili sa magagamit na listahan (ito ang halimbawa ng isang tagamasid). Kapag ang isang kaganapan ay nag-trigger ng wenotify () lahat ng mga nagmamasid na nakapag-iisa-update ang kanilang estado. Sa halimbawang ito, ang nagpapalitaw ay kung ang koponan ng football ng tagamasid ay nakapuntos.

#include 
#include 
gamit ang namespace std;
Paksa ng klase {
    vector  mga tagamasid;
    naka-iskor ang bool; // trigger, kaganapan
pampubliko:
    // magparehistro ng mga tagamasid
    walang kabit ng pag-attach (Observer * obs) {
        tagamasid.push_back (obs);
    }
   
   // Ito ang EVENT
   // itakda ang kung nakapuntos at abisuhan ang LAHAT ng mga tagamasid
   walang bisa setScored (bool Score) {
      nakapuntos = Kalidad;
      ipagbigay-alam ();
   }
bool kumuhaScored () {
      bumalik na marka;
   }
   // ang abisuhan ang pagpapatupad ay mas mababa
   // upang ang script ay nag-iipon at tumatakbo
   walang saysay ();
};

Tagamasid
Ang klase na ito ay nakasalalay sa paksa na nakarehistro ito. Kapag ang mga kongkretong tagamasid ay makakuha ng inisyal na ikinakabit nila ang kanilang mga sarili sa theSubject. Sa halimbawang ito, ang estado ng bawat tagamasid ay ang kanyang kasiyahanLevelabout ang laro.

klase ng Tagamasid
{
    Paksa * sub;
    int excitementLevel; // estado
  pampubliko:
    Tagamasid (Paksang * mod, int excLevel)
    {
        sub = mod;
        kaguluhanLevel = excLevel;
        // Nagparehistro / ilakip ang kanilang sarili sa Paksa
        sub-> ilakip (ito);
    }
    virtual walang bisa na pag-update () = 0;
  protektado:
    Paksa * getSubject () {
       bumalik sub;
    }
    walang bisa na setExcitementLevel (int excLevel) {
       kaguluhanLevel = excLevel;
    }
    int getExcitementLevel () {
       pagbabalik ng kaguluhanLevel;
    }
};

Ito angSubject :: ipagbigay-alam () ang pahayag at tulad ng nabanggit namin bago ang trabaho nito ay ipaalam sa lahat ng mga tagamasid na i-update ang kanilang estado.

walang bisa Paksa :: abisuhan () {
  para sa (int i = 0; i  pag-update ();
}

Mga Tagapanood ng Kongkreto
Ang kongkretong tagamasid ay nagmamana mula sa klase ng Tagamasid at lahat sila ay dapat magkaroon ng pag-update ng function. Sa halimbawang ito, ang mga kongkretong tagamasid ay nakikilala sa pagitan ng mga bata at lumang tagasuporta. Kung ang antas ng kanilang kasiyahan ay nakakakuha ng napakataas na ang mga matatandang tagasuporta ay may panganib na atake sa puso at ang mga nakababata ay may panganib na uminom at magmaneho. Ang kanilang estado ay nag-iisa nang nakapag-iisa tulad namin ay patunayan sa pangunahing pag-andar sa ibaba sa ibaba.

klase Old_ConcreteObserver: pampublikong Tagamasid
{
   pampubliko:
     // Tumatawag ng tagabuo ng magulang upang magparehistro sa paksa
     Old_ConcreteObserver (Paksa * mod, int div)
        : Tagamasid (mod, div) {}
     // Para sa mga matatandang tao, kung ang antas ng kaguluhan
     Ang // ay higit sa 150 tumatakbo sila sa panganib ng atake sa puso
     walang pag-update ()
     {
        bool nakapuntos = getSubject () -> getScored ();
        setExcitementLevel (getExcitementLevel () + 1);
        kung (nakapuntos && getExcitementLevel ()> 150)
        {
          cout << "Nag-iskor ang koponan ng Lumang Tagamasid !!"
               << "Ang kanyang antas ng pagkasabik ay"
               << kumuhaExcitementLevel ()
               << "abangan ang atake sa puso!" << endl;
        } iba pa {
          cout << "Ang koponan ay hindi puntos. Yeeeih walang mag-alala tungkol sa"
               << endl;
        }
    } // pagtatapos ng pag-update ()
};
klase Young_ConcreteObserver: pampublikong Tagamasid
{
   pampubliko:
     // Tumatawag ng tagabuo ng magulang upang magparehistro sa paksa
     Young_ConcreteObserver (Paksa * mod, int div)
       : Tagamasid (mod, div) {}
     // Para sa mga matatandang tao, kung ang antas ng kaguluhan
     // ay higit sa 100 tumatakbo silang peligro sa atake sa puso
     walang pag-update ()
     {
        bool nakapuntos = getSubject () -> getScored ();
        setExcitementLevel (getExcitementLevel () + 1);
        kung (nakapuntos && getExcitementLevel ()> 100)
        {
          cout << "Nag-iskor ang koponan ng Young Observer !!"
               << "Ang kanyang antas ng pagkasabik ay"
               << kumuhaExcitementLevel ()
               << "huwag uminom at magmaneho !!" << endl;
        } iba pa {
          cout << "Ang koponan ay hindi puntos. Yeeh walang mag-alala tungkol sa"
               << endl;
       }
    } // pagtatapos ng pag-update ()
};

Pangunahing pag-andar
Ang kongkretong tagamasid ay nagparehistro sa kanilang sarili sa halimbawa ngSubject. Ang kanilang estado ay ang antas ng kasiyahan na siyang pangalawang parameter. Kapag ang kaganapan ay na-trigger "sub.setScored (totoo)", pagkataposSubject :: abisuhan () ay tinawag na i-update ang mga rehistradong tagamasid. Sa senaryo sa ibaba, mayroon kaming tatlong mga tagamasid, ang youngObs1is na overexcited at nagpapatakbo ng panganib ng inumin at drive, ang oldObs1is ay nasobrahan din ng isang nagpapatakbo ng ibang panganib (sa atake sa puso). Sa wakas, ang mga batangObs2 na bata rin bilang una ay walang dapat alalahanin dahil hindi siya nasasapawan.

Mahalagang mapansin na ang tatlong tagamasid na na-update nang nakapag-iisa batay sa kanilang estado (antas ng kaguluhan) at ang kanilang uri (bata o matanda).
int main () {
   Paksa ng Paksa;
   Young_ConcreteObserver batangObs1 (& sumaklaw, 100);
   Old_ConcreteObserver oldObs1 (& sub, 150);
   Young_ConcreteObserver batangObs2 (at sumailalim, 52);
   sub.setScored (totoo);
}
// Output
// Ang koponan ng batang tagamasid ay binata !! Ang antas ng kanyang kasiyahan ay 101
// huwag uminom at magmaneho !!
// Ang koponan ng Lumang Tagamasid ay naka-iskor !! Ang kanyang antas ng kasiyahan ay 151 relo
// out of atake sa puso! Hindi nakapuntos ang koponan.
// Yeeh walang mag-alala

Mayroong ilang mga benepisyo para sa paggamit ng pattern ng Observer at ilang mga puntos na dapat tandaan kapag ang pattern na ito ay lalapit sa [Learning Python Design Pattern].

  • Ang pattern ng Tagamasid ay nagbibigay ng isang disenyo kung saan ang Paksa at Tagamasid ay maluwag na magkasama. Ang paksa ay hindi kailangang malaman tungkol sa klase ng ConcreteObserver. Ang anumang bagong Manonood ay maaaring idagdag sa anumang oras sa oras. Hindi na kailangang baguhin ang Paksa kapag idinagdag ang isang bagong Tagamasid. Ang mga tagamasid at paksa ay hindi nakatali at hindi nakapag-iisa sa bawat isa, samakatuwid, ang mga pagbabago sa Paksa o Tagamasid ay hindi makakaapekto sa bawat isa.
  • Walang opsyon para sa komposisyon, dahil ang interface ng Tagamasid ay maaaring maging instantiated.
  • Kung ang taga-obserba ay maling nagamit, madali itong magdagdag ng pagiging kumplikado at humantong sa mga isyu sa pagganap.
  • Ang mga notification ay maaaring hindi mapagkakatiwalaan at maaaring magresulta sa mga kondisyon ng lahi o hindi pagkakapareho.

Ang susunod na blog ay magiging isang mabilis na gabay sa pattern ng disenyo ng Bridge. Ito ay isang pattern ng disenyo ng istruktura na ginagamit ng maraming sa industriya. Huwag kalimutan na gusto / ipalakpak ang aking blog-post at sundin ang aking account. Ito ay upang bigyan ako ng kasiyahan na nakatulong ako sa ilang mga kapwa developer at itulak ako upang magpatuloy sa pagsusulat. Kung mayroong isang tukoy na pattern ng disenyo na nais mong malaman tungkol sa pagkatapos ay ipaalam sa akin upang maibigay ko ito para sa iyo sa hinaharap.

Iba pang mga mabilis na gabay sa mga pattern ng disenyo:

  1. Mga pattern ng Disenyo - Isang mabilis na gabay sa Pabrika ng Abstract.
  2. Mga pattern ng Disenyo - Isang mabilis na gabay sa Bridge Pattern.
  3. Mga pattern ng Disenyo - Isang mabilis na gabay sa Tagabuo ng Tagabuo.
  4. Mga pattern ng Disenyo - Isang mabilis na gabay sa Palamuti ng Dekorador.
  5. Mga pattern ng Disenyo - Isang mabilis na gabay sa Facade Pattern.
  6. Mga pattern ng Disenyo - Isang mabilis na gabay sa Observer Pattern.
  7. Mga pattern ng Disenyo - Isang mabilis na gabay sa Singleton Pattern.