2011-11-30 15 views
8

Quando si creano classi POCO che contengono raccolte di tipi primitivi e sono persistenti per codice EF Innanzitutto, il miglior consiglio che ho trovato finora è creare una nuova classe che abbia un ID più il tipo primitivo:Codice quadro entità Prima e raccolte di tipi primitivi

Entity Framework and Models with Simple Arrays

Se ora ho diverse classi che richiedono proprietà di tipo ObservableCollection<string> e sostituirli con ObservableCollection<EntityString> (dove EntityString è un tipo personalizzato con un ID e una proprietà di stringa), io alla fine con un tabella EntityString con più colonne chiave esterna, una per ogni proprietà di tipo ObservableCollection<EntityString> su tutti i tipi di calcestruzzo con tali proprietà.

Ciò comporta un aumento eccessivo delle colonne di chiavi esterne nulle nella tabella EntityString.

Un approccio sarebbe quello di creare una sottoclasse di EntityString e utilizzare il modello Table per Type per tali sottoclassi. Tuttavia, ciò richiede modifiche impreviste al modello di oggetto semplicemente per ospitare Entity Framework.

Domande:

  • è scrivere l'incapsulante il modo migliore per gestire Collection<PrimitiveType>?
  • In tal caso, quali sono i pro ei contro di consentire più (molte) colonne di chiavi esterne rispetto alla creazione di tabelle personalizzate per tipo (al costo di un modello scomodo)?

risposta

5

La promozione del tipo semplice per entità è un'opzione. Se si desidera utilizzare questa nuova entità di tipo primitivo in più relazioni, è meglio rimuovere completamente le proprietà di navigazione da quell'entità e utilizzare l'associazione indipendente (nessuna proprietà FK).

public class StringEntity 
{ 
    public int Id { get; set; } 
    public string Text { get; set; } 
} 

e mappatura:

modelBuilder.Entity<Foo1>().HasMany(f => f.Strings).WithOptional(); 
modelBuilder.Entity<Foo2>().HasMany(f => f.Strings).WithOptional(); 

In banca dati otterrete nuova FK annullabile per principal correlate - non c'è modo di evitarlo, tranne creare speciale StringEntity classe per ogni principale (non usare l'ereditarietà per quello perché influisce sulle prestazioni).

C'è un'alternativa:

public class StringEntity 
{ 
    public int Id { get; set; } 
    public List<string> Strings { get; private set; } 

    public string Text 
    { 
     get 
     { 
      return String.Join(";", Strings); 
     } 

     set 
     { 
      Strings = value.Split(";").ToList(); 
     } 
    } 
} 

In questo caso non è necessario correlato tipo di entità (e tavolo aggiuntivo) ma il vostro soggetto è inquinata con l'aggiunta di proprietà Text che è solo per la persistenza.

+1

Questa soluzione presuppone che un ';' (o qualunque altro carattere magico selezionato) non è un input valido per la stringa di base, corretto? –

+0

È possibile invece esprimere la configurazione fluente 'WithOptional' con gli attributi di classe? Capisco che sono alternative l'una all'altra, ma finora non abbiamo trovato alcuna documentazione completa sull'argomento. –

+0

Se la mappatura predefinita non rende la relazione opzionale non è possibile cambiarla con l'annotazione dei dati. L'annotazione dei dati deve essere posizionata su alcune proprietà, ma in questo caso non vi è alcuna proprietà nell'entità dipendente da utilizzare. –

Problemi correlati