JavaScript: il pattern Decorator

JavaScript: il pattern Decorator

Il pattern Decorator è un'alternativa alla creazione di sottoclassi. Questo pattern può essere usato per includere gli oggetti in un altro oggetto della stessa interfaccia. Ci consente di aggiungere un layer di comportamento ai metodi e di passare la chiamata del metodo all'oggetto originale (ossia al costruttore del decoratore). Vediamone alcuni esempi.

Questo pattern viene usato quando c'è bisogno di aggiungere funzionalità ai metodi sovrascritti. Questo si può ottenere aggiungendo decoratori uno sopra l'altro.

Quali sono i vantaggi di questo pattern? Se teniamo presente quanto detto all'inizio, i decoratori sono un'alternativa alla creazione di sottoclassi. Quando il codice JavaScript viene eseguito, le sottoclassi aggiungono un comportamento che influenza tutte le istanze della classe originale, mentre i decoratori no. Invece si può aggiungere un nuovo comportamento ai singoli oggetti, il che può essere utile a seconda dell'applicazione.

Un esempio:


// La classe da decorare

function Macbook(){

      this.cost = function(){
      
      return 1000;

     };

}

 

function Memory(macbook){

    this.cost = function(){

     return macbook.cost() + 75;

  };

}

 

function BlurayDrive(macbook){

   this.cost = function(){

     return macbook.cost() + 300;

  };

}



function Insurance(macbook){

   this.cost = function(){

     return macbook.cost() + 250;

  };

}


var myMacbook = new Insurance(new BlurayDrive(new Memory(new Macbook())));
console.log( myMacbook.cost() );

Ecco un altro esempio di decoratore dove quando invochiamo performTask() sull'oggetto decoratore viene aggiunto sia del comportamento che un'esecuzione nel contesto dell'oggetto sottostante:


function ConcreteClass(){

    this.performTask = function() {

        this.preTask();

        console.log('Azione');

        this.postTask();

    };

}

 

function AbstractDecorator(decorated){

    this.performTask = function() {

        decorated.performTask();

    };
}

 

function ConcreteDecoratorClass(decorated){

    this.base = AbstractDecorator;

    this.base(decorated);

     

    this.preTask = function() {
    
        console.log('prechiamata..');

    };
     
     
    this.postTask = function() {
    
        console.log('postchiamata..');

    };

     

}

 

var concrete = new ConcreteClass();

var decorator1 = new ConcreteDecoratorClass(concrete);

var decorator2 = new ConcreteDecoratorClass(decorator1);

decorator2.performTask();
Torna su