2009-10-10 8 views
5

Stavo solo leggendo su inversion of control (IOC) e mi dava fastidio il fatto che sembrasse che la gestione della memoria fosse un problema. Ovviamente sembra che ioc sia usato principalmente in ambienti garbage collection (Net, Java, Scripting), mentre la mia preoccupazione è nelle impostazioni non gc.L'inversione del controllo e RAII possono giocare insieme?

La mia preoccupazione è che l'IOC in qualche modo vada contro RAII, dal momento che separiamo la vita delle risorse dalla vita dell'oggetto. Questa complessità aggiuntiva non infastidisce nessun altro? E la vera domanda, quali tecniche possono essere utilizzate per rendere le cose senza intoppi?

+0

Vedere anche http://stackoverflow.com/questions/987761/how-do-you-reconcile-idisposable-and-ioc e http://unity.codeplex.com/Thread/View.aspx?ThreadId=38588 – TrueWill

risposta

3

Proprio per questo motivo ho creato il mio contenitore IoC che restituisce (in C# /. NET) i wrapper di servizio usa e getta che, una volta smaltiti, "faranno la cosa giusta" per quanto riguarda il servizio.

Che si tratti di:

  • Non fare nulla, quando:
    • L'oggetto non significa implementare IDisposable
    • non è il contenitore con ambito (nel qual caso il contenitore non mancherà di tenere traccia di esso e il ritorno lo stesso oggetto più di una volta, e quando il contenitore viene eliminato, l'oggetto sarà troppo)
    • Non raggruppato
    • Non è singleton con scope (stesso contenitore con scope, ma una gerarchia di contenitori memorizzerà il servizio singleton con ambito nel contenitore più alto)
  • smaltimento del servizio (ha portata fabbrica, e implementa IDisposable)
  • Return al pool

Ciò significa che tutto il codice che utilizza i miei servizi è all'interno di un utilizzando blocco, ma l'intento è più chiaro, almeno per me:

using (var service = container.Resolve<ISomeService>()) 
{ 
    service.Instance.SomeMethod(); 
} 

fondamentalmente iT SA ys: risolve un servizio, chiama SomeMethod sull'istanza del servizio, quindi elimina il servizio.

Poiché la conoscenza dell'eliminazione dell'istanza del servizio o non è disponibile per il consumatore, è stata scelta la possibilità di ignorare del tutto le implementazioni IDisposable o di eliminare tutti i servizi che implementano IDisposable. Nessuna delle due era una buona soluzione per me.La terza scelta era di avvolgere l'istanza del servizio in un oggetto che sapeva cosa fare con il servizio una volta che il wrapper era stato eliminato.

+0

A volte l'antropomorfo 'IDisposable' finisce per essere inevitabile (come quando si usa' foreach' su un tipo che implementa un metodo 'GetEnumerator()' utilizzabile ma non implementa 'IEnumerable '), ma è un odore importante dal momento che si noti il ​​fatto che una classe contiene un riferimento a qualcosa che implementa 'IDisposable' non implica sempre che" possiede "l'oggetto a cui si riferisce. – supercat

0

La prima cosa a cui potevo pensare era SmartPointers. E argomenti del modello. Ma non sono sicuro che gli argomenti modello contino come una tecnica IOC, anche se penso che dovrebbero. Almeno questi possono alleviare alcuni problemi con IOC, ma non totalmente venduti sull'idea.

1

Sì e no. IoC non separa la durata della risorsa dalla vita dell'oggetto, disaccoppia l'ambito di chiamata del metodo dalla durata dell'oggetto: molto spesso desideri che l'oggetto venga distrutto alla fine di un metodo finché non viene effettuata un'altra chiamata IoC. Quindi devi spostare i locals di un metodo in ambito di classe, e assicurarti che nessun metodo rientri, o adottare un altro approccio, come avere un "ambiente" extra passato per consentire agli oggetti di essere posseduti da questo, e distrutto nelle successive chiamate al metodo IoC. Entrambi gli approcci diventano piuttosto complicati se si desidera un sistema basato su eventi generico: i modelli finiscono per dover implementare la ricorsione e l'iterazione esplicite oppure il semplice codice RAII C++ diventa rapidamente un complesso complesso di callback, sufficientemente complesso da abbandonare su C++ e RAII ha iniziato a lavorare su kin invece.

Problemi correlati