Pregunta

Tengo una clase genérica

public MyClass<TContext, T> where TContext : DataContext

que actúa efectivamente en una instancia de otra

public class MyOtherClass<T> : IEnumerable<T>

Quiero hacer cumplir que el TContext tiene un Table<T>. ¿Hay una manera limpia de hacer cumplir esto?

¿Fue útil?

Solución

¿Desea verificar que TContext tiene un miembro que es una Tabla < T > ;? Si es así, la única forma de hacerlo es definir una interfaz para este contrato y modificar sus restricciones genéricas

interface IMyTable<T> {
  Table<T> Table;
}

public MyClass<TContext,T> where TContext : DataContext,IMyTable<T>

EDIT

Jason publicó un comentario aclaratorio a mi respuesta. El nombre Tabla no es estático, sino que depende del tipo de T.

Si ese es el caso, entonces no hay forma de aplicarlo estáticamente a través de restricciones genéricas. Lo mejor que puede hacer es crear una clase de adaptador que implemente IMyTable & Lt; & Gt; y proporciona un DataContext y una instancia de Table.

interface IMyTable2<T> {
  DataContext DataContext {get; }
  Table<T> Table {get; }
}

class MyAdapter: IMyTable2<T> {
  private MyOtherClass<T> _other;
  public DataContext DataContext { get { return _other.DataContext } }
  public Table<T> Table { get { return _other.TableWithDifferentName; } }
}

Otros consejos

Creo que JaredPar tuvo la idea correcta la primera vez.

interface IMyTable<T>
{
  Table<T> TheTable {get;}
}

public class MyClass<TContext,T> where
  TContext : DataContext,IMyTable<T>
{
  //silly implementation provided to support the later example:
  public TContext Source {get;set;}

  public List<T> GetThem()
  {
    IMyTable<T> x = Source as IMyTable<T>;
    return x.TheTable.ToList(); 
  }
}

Quiero ampliar su pensamiento agregando una implementación de interfaz explícita. Esto aborda el comentario de Jason sobre el acceso a la propiedad de la tabla a través de IMyTable. El tipo debe estar involucrado de alguna manera, y si tiene un IMyTable<T>, el tipo está involucrado.

public partial class MyDataContext:IMyTable<Customer>, IMyTable<Order>
{
  Table<Customer> IMyTable<Customer>.TheTable
  { get{ return this.GetTable<Customer>(); } }

  Table<Order> IMyTable<Order>.TheTable
  { get{ return this.GetTable<Order>(); } }  
}

Ahora es posible hacer esto:

var z = new MyClass<MyDataContext, Customer>();
z.Source = new MyDataContext();
List<Customer> result = z.GetThem();

la única forma de aplicarla es si Table estaba en una interfaz, y usted le asignó una restricción genérica ... así que algo así como

public class MyOtherClass<T> : IEnumerable<T>, IHasTable<T>
Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top