2010-05-31 13 views
12

Ho un (Object Plain Old CLR) POCOEntity Framework 4 POCO con dizionario

public Foo 
{ 
    public virtual int Id { get; set; } 
    public virtual Dictionary<string, string> Stuff { get; set; } 
    public virtual string More { get; set; } 
} 

Utilizzando l'approccio model first (cioè non ho un modello di dati ancora), come sarebbe mi occupo persistente Stuff (Dizionario)?

risposta

7

Questa non è una risposta vera alla domanda, ma poiché non ci sono altre risposte, condividerò ciò che ho fatto.

Ho semplicemente creato un nuovo tipo {Id, Code, Text} e sostituito il mio dizionario con un elenco di quel tipo. Ho poi fare qualcosa di simile per ottenere le chiavi, valori, o fare una ricerca:

List<string> texts = (from sv in q.SelectableValues select sv.Text).ToList(); 
List<string> codes = (from sv in q.SelectableValues select sv.Code).ToList(); 
string text = (from sv in q.SelectableValues where sv.Code == "MyKey" select sv.Text).First(); 

Nel mio caso il numero di voci nel dizionario tende ad essere di piccole dimensioni. Tuttavia, vedere this question per considerazioni sulle prestazioni quando il dizionario/elenco è grande.

7

Sembra che il modo corretto e persistente per mantenere un dizionario in un database sia il modo in cui è enumerato, poiché le tabelle sono essenzialmente insiemi con un concetto di ordine allentato, proprio come IEnumerable. Cioè, un dizionario viene enumerato come IEnumerator < KeyValuePair < TKey, TValue>>, e così il tavolo dovrebbe avere 2 colonne:

Key 
Value 

Da lì si hanno le convenzioni EF esistenti di tipi complessi, dove la chiave potrebbe effettivamente essere un oggetto con molte proprietà e valore pure. Ad esempio, un dizionario di oggetti utente potrebbe essere simile:

Username (TKey) 
Address1 (TValue) 
Address2 (TValue) 

E 'un peccato questo schema generalizzato non è built-in per EF; dovrebbe essere proposto.

Invece di sviluppare un tipo specifico per la soluzione, è possibile utilizzare una classe generalizzata che produce una versione annotata dei dati di KeyValuePair <>.

public class EFKeyValuePair<TKey, TValue> 
{ 
    [Key] 
    public TKey Key { get; set; } 
    public TValue Value { get; set; } 
} 

Io non sono certo come ci si assicura i nomi delle tabelle sarebbero scritti in maniera logica e verificabile tuttavia senza ereditare questa classe e l'aggiunta di un attributo per ogni sottoclasse. Forse l'API Fluent potrebbe farti fare questo passo finale (che non mi è molto familiare).

Problemi correlati