Qual è la differenza tra il modello di progettazione strategica e il modello di progettazione statale?


219

Quali sono le differenze tra il modello di progettazione strategica e il modello di progettazione statale? Stavo leggendo alcuni articoli sul web ma non riuscivo a capire chiaramente la differenza.

Qualcuno può spiegare la differenza nei termini dei laici?


Sulla base delle risposte qui e delle mie osservazioni, sembra che le implementazioni siano sostanzialmente (anche se non del tutto) le stesse. Piuttosto, la differenza è principalmente nell'intento: stiamo cercando di adattare il comportamento, sia in base al nostro stato (modello di stato), o in base a qualcos'altro (modello di strategia). Molto spesso qualcos'altro è "ciò che il cliente sceglie", attraverso l'iniezione.
Timo

Risposte:


139

Onestamente, i due modelli sono abbastanza simili nella pratica e la differenza che li definisce tende a variare a seconda di chi chiedi. Alcune scelte popolari sono:

  • Gli stati memorizzano un riferimento all'oggetto contesto che li contiene. Le strategie no.
  • Gli Stati possono sostituire se stessi (IE: cambiare lo stato dell'oggetto contestuale in qualcos'altro), mentre le Strategie no.
  • Le strategie vengono passate all'oggetto contesto come parametri, mentre gli Stati vengono creati dall'oggetto contesto stesso.
  • Le strategie gestiscono solo un singolo compito specifico, mentre gli Stati forniscono l'implementazione sottostante per tutto (o quasi tutto) l'oggetto contestuale.

Un'implementazione "classica" corrisponderebbe a Stato o Strategia per ogni elemento dell'elenco, ma ti imbatti in ibridi che hanno mix di entrambi. Se uno in particolare è più stato-y o strategia-y è in definitiva una domanda soggettiva.


6
Se si considera il GoF come una delle scelte popolari, non sarebbero d'accordo sul fatto che gli Stati siano necessariamente creati dal contesto (possono essere creati dal cliente e passati al contesto, proprio come con la strategia).
Will Hardwick-Smith,

109
  • Il modello di strategia riguarda in realtà un'implementazione diversa che realizza (sostanzialmente) la stessa cosa, in modo che un'implementazione possa sostituire l'altra come richiesto dalla strategia. Ad esempio, potresti avere algoritmi di ordinamento diversi in un modello di strategia. I chiamanti per l'oggetto non cambiano in base alla strategia utilizzata, ma indipendentemente dalla strategia l'obiettivo è lo stesso (ordinare la raccolta).
  • Il modello statale consiste nel fare diverse cose in base allo stato, lasciando il chiamante sollevato dall'onere di accogliere ogni stato possibile. Quindi, ad esempio, potresti avere un getStatus()metodo che restituirà stati diversi in base allo stato dell'oggetto, ma il chiamante del metodo non deve essere codificato in modo diverso per tenere conto di ogni potenziale stato.

1
ma chi cambia la strategia nel modello di strategia ??
Noor

1
@Noor, di solito è un parametro o un campo di qualche tipo. Il codice del chiamante effettivo non viene modificato in base a una modifica della strategia.
Yishai

4
@Noor, sì, ma in qualsiasi modello di strategia che mi viene in mente in questo momento, sarà una decisione anticipata che non cambierà nel mezzo.
Yishai

2
Sono con lo stesso problema, stato o strategia, penso che la differenza in poche parole sia, stato, comportamento autodeterminato, strategia, comportamento determinato dal chiamante.
Rene MF

1
Nell'applicazione e-commerce, se è necessario applicare uno sconto extra durante le festività, si tratta di un modello di progettazione statale. La logica del tasso di sconto effettivo può essere applicata con il modello di progettazione della strategia, se esistono più modi per arrivare a quel numero.
Bharathkumar V

85

La differenza sta semplicemente nel fatto che risolvono diversi problemi:

  • Il modello di stato si occupa di quale (stato o tipo) è un oggetto (in) - incapsula il comportamento dipendente dallo stato, mentre
  • il modello di strategia si occupa di come un oggetto esegue un determinato compito - incapsula un algoritmo.

I costrutti per raggiungere questi diversi obiettivi sono comunque molto simili; entrambi i modelli sono esempi di composizione con delega.


Alcune osservazioni sui loro vantaggi:

Usando lo Stato modello del (contesto) di classe-holding di stato si assumono la conoscenza di ciò che stato o tipo è e ciò che afferma o tipi che sono disponibili. Ciò significa che la classe aderisce al principio di progettazione aperto-chiuso (OCP): la classe è chiusa per modifiche in quali stati / tipi ci sono, ma gli stati / tipi sono aperti alle estensioni.

Usando il modello di strategia , la classe che utilizza l'algoritmo (contesto) viene sollevata dalla conoscenza di come eseguire un determinato compito (- "l'algoritmo"). Questo caso crea anche un'adesione all'OCP; la classe è chiusa per modifiche su come eseguire questa attività, ma la progettazione è molto aperta alle aggiunte di altri algoritmi per risolvere questa attività.
Ciò probabilmente migliora anche l'adesione della classe di contesto al principio della responsabilità singola (SRP). Inoltre l'algoritmo diventa facilmente disponibile per il riutilizzo da parte di altre classi.


42

Qualcuno può spiegare in parole povere?

I modelli di progettazione non sono in realtà concetti "laici", ma cercherò di renderlo il più chiaro possibile. Qualsiasi modello di progettazione può essere considerato in tre dimensioni:

  1. Il problema risolto dal modello;
  2. La struttura statica del modello (diagramma di classe);
  3. La dinamica del modello (diagrammi di sequenza).

Confrontiamo Stato e Strategia.

Problema risolto dal modello

Lo stato viene utilizzato in uno dei due casi [libro GoF p. 306] :

  • Il comportamento di un oggetto dipende dal suo stato e deve cambiare il suo comportamento in fase di esecuzione a seconda di quello stato.
  • Le operazioni hanno grandi istruzioni condizionali multipart che dipendono dallo stato dell'oggetto. Questo stato è generalmente rappresentato da una o più costanti enumerate. Spesso, diverse operazioni conterranno la stessa struttura condizionale. Il modello di stato mette ogni ramo del condizionale in una classe separata. Ciò consente di trattare lo stato dell'oggetto come un oggetto a sé stante che può variare indipendentemente dagli altri oggetti.

Se vuoi assicurarti di avere effettivamente il problema risolto dal modello di stato, dovresti essere in grado di modellare gli stati dell'oggetto usando una macchina a stati finiti . Puoi trovare un esempio applicato qui .

Ogni transizione di stato è un metodo nell'interfaccia di stato. Ciò implica che, per un progetto, devi essere abbastanza sicuro delle transizioni di stato prima di applicare questo modello. Altrimenti, se aggiungi o rimuovi transizioni, dovrai cambiare l'interfaccia e tutte le classi che la implementano.

Personalmente non ho trovato questo schema così utile. Puoi sempre implementare macchine a stati finiti usando una tabella di ricerca (non è un metodo OO, ma funziona abbastanza bene).

La strategia viene utilizzata per il seguente [libro GoF p. 316] :

  • molte classi correlate differiscono solo nel loro comportamento. Le strategie forniscono un modo per configurare una classe con uno dei tanti comportamenti.
  • hai bisogno di diverse varianti di un algoritmo. Ad esempio, è possibile definire algoritmi che riflettono diversi compromessi spazio / tempo. Le strategie possono essere utilizzate quando queste varianti sono implementate come una gerarchia di classi di algoritmi [HO87].
  • un algoritmo utilizza dati che i clienti non dovrebbero conoscere. Utilizzare il modello di strategia per evitare di esporre strutture di dati complesse, specifiche dell'algoritmo.
  • una classe definisce molti comportamenti e questi compaiono come più istruzioni condizionali nelle sue operazioni. Invece di molti condizionali, sposta i relativi rami condizionali nella propria classe Strategia.

L'ultimo caso di dove applicare la strategia è legato a un refactoring noto come Sostituisci condizionato con polimorfismo .

Riepilogo: Stato e strategia risolvono problemi molto diversi. Se il problema non può essere modellato con una macchina a stati finiti, probabilmente il modello di stato non è appropriato. Se il tuo problema non riguarda l'incapsulamento delle varianti di un algoritmo complesso, la Strategia non si applica.

Struttura statica del modello

State ha la seguente struttura di classe UML:

Diagramma di classe PlantUML del modello di stato

La strategia ha la seguente struttura di classe UML:

Diagramma di classe PlantUML del modello di strategia

Riepilogo: in termini di struttura statica, questi due modelli sono per lo più identici. In effetti, strumenti di rilevamento dei modelli come questo ritengono che " la struttura dei [...] modelli è identica, vietandone la distinzione mediante un processo automatico (ad esempio, senza fare riferimento a informazioni concettuali) " .

Tuttavia, può esserci una grande differenza se ConcreteStates decide autonomamente le transizioni di stato (vedere le associazioni " potrebbero determinare " nel diagramma sopra). Ciò si traduce in accoppiamento tra stati concreti. Ad esempio (vedere la sezione successiva), lo stato A determina la transizione allo stato B. Se la classe Context decide la transizione allo stato concreto successivo, queste dipendenze scompaiono.

Dinamica del modello

Come menzionato nella sezione Problema sopra, lo stato implica che il comportamento cambia in fase di esecuzione in base a uno stato di un oggetto. Pertanto, la nozione di transizione di stato applica , come discusso con la relazione della macchina a stati finiti . [GoF] menziona che le transizioni possono essere definite nelle sottoclassi ConcreteState o in una posizione centralizzata (come una posizione basata su tabella).

Supponiamo che una semplice macchina a stati finiti:

Diagramma di transizione dello stato PlantUML con due stati e una transizione

Supponendo che le sottoclassi decidano la transizione di stato (restituendo il successivo oggetto di stato), la dinamica è simile a questa:

Diagramma di sequenza PlantUML per le transizioni di stato

Per mostrare le dinamiche della strategia , è utile prendere in prestito un esempio reale .

Diagramma di sequenza PlantUML per le transizioni strategiche

Riepilogo : ogni modello utilizza una chiamata polimorfica per fare qualcosa a seconda del contesto. Nel modello di stato, la chiamata polimorfica (transizione) spesso provoca un cambiamento nello stato successivo . Nel modello di strategia, la chiamata polimorfica in genere non cambia il contesto (ad esempio, il pagamento con carta di credito una volta non implica che il pagamento verrà effettuato da PayPal la volta successiva). Ancora una volta, le dinamiche del modello statale sono determinate dalla relativa macchina a stati finiti, che (per me) è essenziale per la corretta applicazione di questo modello.


Questa risposta mi è stata molto utile per farmi distinguere la differenza. L'argomento della macchina a stati sembra essere IMHO pertinente. Questo in realtà riassume le risposte di cui sopra in un modo teorico dell'informatica.
medunes,

Questa risposta è molto utile, per me questa è la migliore.
Chofoteddy,

25

Il modello di strategia prevede lo spostamento dell'implementazione di un algoritmo da una classe di hosting e l'inserimento in una classe separata. Ciò significa che la classe host non deve fornire l'implementazione di ciascun algoritmo stesso, il che probabilmente porterà a codice sporco.

Gli algoritmi di ordinamento sono generalmente usati come esempio poiché fanno tutti lo stesso tipo di cose (ordinamento). Se ogni algoritmo di ordinamento diverso viene inserito nella propria classe, il client può facilmente scegliere quale algoritmo utilizzare e il modello fornisce un modo semplice per accedervi.

Il modello di stato comporta la modifica del comportamento di un oggetto quando lo stato dell'oggetto cambia. Ciò significa che la classe host non deve fornire l'implementazione del comportamento per tutti i diversi stati in cui può trovarsi. La classe host di solito incapsula una classe che fornisce la funzionalità richiesta in un determinato stato e passa a una classe diversa quando lo stato cambia.


16

Prendi in considerazione un sistema IVR (Interactive Voice Response) che gestisce le chiamate dei clienti. Potresti programmarlo per gestire i clienti su:

  • Giorni lavorativi
  • Vacanze

Per gestire questa situazione è possibile utilizzare un modello di stato .

  • Festività : IVR risponde semplicemente dicendo che "Le chiamate possono essere prese solo nei giorni lavorativi tra le 9:00 e le 17:00 ".
  • Giorni lavorativi : risponde collegando il cliente a un dirigente dell'assistenza clienti.

Questo processo di connessione di un cliente a un dirigente del supporto può essere implementato mediante un modello di strategia in cui i dirigenti vengono scelti in base a uno dei seguenti:

  • Round Robin
  • Usato di recente
  • Altri algoritmi basati su priorità

Il modello di strategia decide su " come " eseguire alcune azioni e il modello di stato decide su " quando " eseguirle.


Questa è una risposta eccellente e sottovalutata. Ma sarebbe utile menzionare il motivo per cui nel tuo esempio sono necessari molti algoritmi. Ad esempio, l'algoritmo viene scelto in base alle preferenze dell'azienda del call center. Sarebbe anche utile se ci fossero algoritmi più semplici o banali nella tua lista per coloro che non conoscono RR o LRU. Ad esempio: il cliente di lunga data ha una priorità maggiore, il cliente che ha atteso di più ha una priorità maggiore. Grazie !
MasterJoe2

14

La strategia rappresenta oggetti che "fanno" qualcosa, con gli stessi risultati di inizio e fine, ma internamente utilizzando metodologie diverse. In tal senso sono analoghi a rappresentare l'implementazione di un verbo. Il modello di stato OTOH utilizza oggetti che "sono" qualcosa: lo stato di un'operazione. Sebbene possano rappresentare anche operazioni su tali dati, sono più analoghi alla rappresentazione di un sostantivo che a un verbo e sono adattati alle macchine a stati.


11

Strategia: la strategia è fissa e di solito consiste in diversi passaggi. (L'ordinamento costituisce solo un passo e quindi è un pessimo esempio in quanto è troppo primitivo per comprendere lo scopo di questo modello). La tua routine "principale" nella strategia sta chiamando alcuni metodi astratti. Ad esempio "Enter Room Strategy", "main-method" è goThroughDoor (), che assomiglia a: approachDoor (), if (lock ()) openLock (); porta aperta(); enterRoom (); ruotare (); chiudi la porta(); if (wasLocked ()) lockDoor ();

Ora le sottoclassi di questo "algoritmo" generale per spostarsi da una stanza all'altra attraverso una possibile porta bloccata possono implementare i passaggi dell'algoritmo.

In altre parole, la sottoclasse della strategia non modifica gli algoritmi di base, ma solo i singoli passaggi.

CHE SOPRA è un modello di modello. Ora metti i passaggi che appartengono insieme (sblocco / blocco e apertura / chiusura) nei loro oggetti di implementazione e delegali ad essi. Ad esempio un lucchetto con una chiave e un lucchetto con una scheda di codice sono due tipi di lucchetti. Delegare dalla strategia agli oggetti "Step". Ora hai un modello di strategia.

Un modello di stato è qualcosa di completamente diverso.

Hai un oggetto avvolgente e l'oggetto avvolto. Quello avvolto è lo "stato". L'oggetto state è accessibile solo tramite il suo wrapper. Ora puoi cambiare l'oggetto spostato in qualsiasi momento, quindi il wrapper sembra cambiare il suo stato, o anche la sua "classe" o tipo.

Ad esempio, hai un servizio di accesso. Accetta un nome utente e una password. Ha solo un metodo: accesso (String userName, String passwdHash). Invece di decidere autonomamente se accettare o meno un accesso, delega la decisione a un oggetto stato. Quell'oggetto stato di solito controlla solo se la combinazione utente / pass è valida ed esegue un accesso. Ma ora è possibile scambiare il "Checker" con uno che consente l'accesso solo agli utenti privilegiati (ad esempio durante il periodo di manutenzione) o con uno che non consente l'accesso a nessuno. Ciò significa che il "checker" esprime lo "stato di accesso" del sistema.

La differenza più importante è: quando hai scelto una strategia, la segui fino a quando non hai finito. Ciò significa che lo chiami "metodo principale" e fintanto che quello in esecuzione non cambi mai la strategia. OTOH in una situazione di stato durante il runtime del tuo sistema, cambi stato arbitrariamente come ritieni opportuno.


9

Strategia modello di viene utilizzato quando si dispone di più algoritmi per un'attività specifica e il client decide l'implementazione effettiva da utilizzare in fase di esecuzione.

Diagramma UML dall'articolo del modello di strategia wiki :

inserisci qui la descrizione dell'immagine

Caratteristiche principali:

  1. È un modello comportamentale.
  2. Si basa sulla delega.
  3. Cambia l'intestino dell'oggetto modificando il comportamento del metodo.
  4. È usato per passare da una famiglia di algoritmi a un'altra.
  5. Cambia il comportamento dell'oggetto in fase di esecuzione.

Fare riferimento a questo post per ulteriori informazioni ed esempi del mondo reale:

Esempio reale del modello di strategia

Stato modello di consente a un oggetto di modificare il suo comportamento quando cambia il suo stato interno

Diagramma UML dall'articolo del modello di stato wiki :

inserisci qui la descrizione dell'immagine

Se dobbiamo modificare il comportamento di un oggetto in base al suo stato, possiamo avere una variabile di stato nell'oggetto e utilizzare il blocco di condizioni if-else per eseguire diverse azioni in base allo stato. Il modello di stato viene utilizzato per fornire un modo sistematico e accoppiato per raggiungere questo obiettivo attraverso il contesto e lo stato implementazioni .

Fare riferimento a questo articolo di journaldev per maggiori dettagli.

Principali differenze rispetto agli articoli di produzione di sorgenti e journaldev :

  1. La differenza tra Stato e Strategia sta nel tempo vincolante. La strategia è un modello vincolante, mentre lo stato è più dinamico .
  2. La differenza tra Stato e Strategia è nell'intento. Con la strategia, la scelta dell'algoritmo è abbastanza stabile . Con State, un cambiamento nello stato dell'oggetto "contesto" lo fa selezionare dalla sua "tavolozza" di oggetti Strategia .
  3. Il contesto contiene lo stato come variabile di istanza e possono essere presenti più attività la cui implementazione può dipendere dallo stato, mentre nella strategia del modello di strategia la strategia viene passata come argomento al metodo e l' oggetto di contesto non ha alcuna variabile per memorizzarlo.

5

Nella lingua dei laici,

nel modello di strategia, non ci sono stati o tutti hanno lo stesso stato. Tutti hanno diversi modi di svolgere un compito, come diversi medici trattano la stessa malattia dello stesso paziente con lo stesso stato in modi diversi.

Nel modello di stato, soggettivamente ci sono stati, come lo stato attuale del paziente (ad esempio alta temperatura o bassa temperatura), in base al quale verrà deciso il prossimo corso di azione (prescrizione di medicina). E uno stato può portare ad un altro stato, quindi c'è stato dichiarare dipendenza (composizione tecnicamente).

Se tecnicamente proviamo a capirlo, basandoci sul confronto del codice di entrambi, potremmo perdere la soggettività della situazione, perché entrambi sembrano molto simili.


2

Entrambi i modelli delegano a una classe base che ha diverse derivate, ma è solo nel modello State che queste classi derivate contengono un riferimento alla classe di contesto.

Un altro modo di vederlo è che il modello di strategia è una versione più semplice del modello di stato; uno schema secondario, se lo desideri. Dipende davvero se si desidera che gli stati derivati ​​trattengano i riferimenti al contesto o meno (ad esempio: si desidera che chiamino metodi nel contesto).

Per maggiori informazioni: Robert C Martin (e Micah Martin) rispondono nel loro libro "Principi, schemi e pratiche agili in C #". ( http://www.amazon.com/Agile-Principles-Patterns-Practices-C/dp/0131857258 )


2

Questa è una domanda piuttosto vecchia, ma cercavo sempre le stesse risposte e questo è quello che ho scoperto.

Per il modello di stato, prendiamo in considerazione un esempio del pulsante Play di Medial Player. Quando lo facciamo inizia a suonare e rende il contesto consapevole che sta giocando. Ogni volta che il cliente desidera eseguire un'operazione di gioco, verifica lo stato corrente del giocatore. Ora il client sa che lo stato dell'oggetto viene riprodotto tramite l'oggetto di contesto, quindi chiama il metodo delle azioni degli oggetti stato di pausa. La parte del client che realizza lo stato e su quale stato deve compiere un'azione può essere automatizzata.

https://www.youtube.com/watch?v=e45RMc76884 https://www.tutorialspoint.com/design_pattern/state_pattern.htm

Nel caso del modello di strategia, la disposizione del diagramma di classe è la stessa del modello di stato. Il cliente arriva a questo accordo per fare qualche operazione. Cioè invece dei diversi stati ci sono algoritmi diversi che dicono ad esempio analisi diverse che devono essere eseguite sul modello. Qui i clienti dicono al contesto cosa vuole fare e quale algoritmo (algoritmo personalizzato definito dal business) e quindi lo eseguono.

https://www.tutorialspoint.com/design_pattern/strategy_pattern.htm

Entrambi implementano il principio open close in modo che lo sviluppatore abbia la capacità di aggiungere nuovi stati al modello di stato e al nuovo algoritmo.

Ma la differenza è ciò che viene utilizzato, ovvero il modello di stato utilizzato per eseguire una logica diversa in base a uno stato dell'oggetto. E in un caso di strategia logica diversa.


2

Lo stato ha delle dipendenze un po 'all'interno delle classi derivate dallo stato: come uno stato sa di altri stati che lo inseguono. Ad esempio, l'estate arriva dopo l'inverno per qualsiasi stato di stagione o lo stato di consegna dopo lo stato di deposito per lo shopping.

D'altra parte, la strategia non ha dipendenze come queste. Qui, qualsiasi tipo di stato può essere inizializzato in base al tipo di programma / prodotto.


1

La differenza è discussa in http://c2.com/cgi/wiki?StrategyPattern . Ho usato il modello di strategia per consentire la scelta di diversi algoritmi in un quadro generale per l'analisi dei dati. Attraverso ciò è possibile aggiungere algoritmi senza dover cambiare i quadri generali e la sua logica.

Un tipico esempio è che hai un framework per ottimizzare una funzione. Il framework imposta dati e parametri. Il modello di strategia consente di selezionare algoritmi come discese sttepest, gradienti coniugati, BFGS, ecc. Senza alterare il framework.


1

Sia la strategia che il modello statale hanno la stessa struttura. Se guardi il diagramma di classe UML per entrambi i modelli, sembrano esattamente uguali, ma il loro intento è totalmente diverso. Il modello di progettazione dello stato viene utilizzato per definire e gestire lo stato di un oggetto, mentre il modello di strategia viene utilizzato per definire una serie di algoritmi intercambiabili e consente al cliente di sceglierne uno. Quindi il modello di strategia è un modello guidato dal client mentre Object può gestire lo stato stesso.


1

In breve, con il modello di strategia possiamo impostare alcuni comportamenti al volo, con il modello di stato, possiamo essere certi che un oggetto cambierà il suo comportamento internamente con il cambiamento del suo stato.


0

Quando hai un progetto che può essere diviso in 2 attività:

attività 1: è possibile utilizzare uno dei due algoritmi diversi per eseguire: alg1, alg2

attività 2: è possibile utilizzare uno dei tre algoritmi diversi per eseguire: alg3, alg4, alg5

alg1 e alg2 sono intercambiabili; alg3, alg4 e alg5 sono intercambiabili.

La scelta dell'algoritmo da eseguire nell'attività 1 e nell'attività 2 dipende dagli stati:

stato 1: è necessario alg1 nell'attività 1 e alg3 nell'attività 2

stato 2: è necessario alg2 nell'attività 1 e alg5 nell'attività 2

Il contesto può cambiare l'oggetto stato dallo stato 1 allo stato 2. Quindi l'attività verrà eseguita da alg2 e alg5, invece di alg1 e alg3.

È possibile aggiungere altri algoritmi intercambiabili per l'attività 1 o l'attività 2. Questo è il modello di strategia.

È possibile avere più stati con diversa combinazione di algoritmi nell'attività 1 e nell'attività 2. Il modello di stato consente di passare da uno stato all'altro ed eseguire diverse combinazioni di algoritmi.


0

La "strategia" è solo un algoritmo che puoi cambiarlo in diverse circostanze in base alle tue necessità, ed elabora qualcosa per te. Ex. puoi scegliere come comprimere un file. zip o rar ... in un metodo.

Ma 'State' PU change cambiare tutto il comportamento dell'oggetto, quando cambia, anche se può cambiare altri campi ... ecco perché ha un riferimento al suo proprietario. Dovresti notare che cambiare un campo oggetto può cambiare il comportamento dell'oggetto. Ex. quando cambiate State0 in State1 in obj, cambiate un numero intero in 10 .. quindi quando chiamiamo obj.f0 () che fa un calcolo e usiamo quel numero intero, influenza il risultato.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.