Martin Fowler, nel suo libro Patterns of Enterprise Application Architecture, parla delle varie possibilità di mappare il mondo OO con quello relazionale (DB). Uno dei punti interessanti riguarda l'identificazione univoca dell'oggetto vs quella dell'entità nel DB (sia essa una tabella oppure un insieme di tabelle - dovuto a forme di normalizzazione). Sostanzialmente, un oggetto viene univocamente identificato attraverso il suo indirizzo in memoria (puntatore), mentre nel database dalla sua chiave primaria (potrebbe anche essere una combinazione di campi). Martin, suggerisce di mantenere all'interno dell'oggetto i campi rappresentanti la chiave primaria nel database.

In C# 1.x questo verrebbe raggiunto attraverso un campo generico (object) in quanto soddisferebbe tutte le tipologie di chiave, quindi:

public class Persona { public object codice; /*.... */}

In C# 2.0 è possibile dichiarare un tipo generico che si mappi su tutti i possibili tipi disponibili. Ad esempio:

public class Key<T>
{
 private T _value;

 public Key() { }

 public Key(T value)
 {
  if (value == null)
   _value = default(T);
  else
   _value = value;
 }

 public override string ToString()
 {
  return (_value == null) ? "" : _value.ToString();
 }

 public static implicit operator Key<T>(T value)
 {
  return new Key<T>(value);
 }

 public static implicit operator T(Key<T> value)
 {
  if (value == null)
   return default(T);
  else
   return value._value;
 }
}

Gli operatori di conversione permettono di passare da un tipo generico ad uno concreto e viceversa in modo del tutto trasparente.