Question

j'ai une classe générique

public MyClass<TContext, T> where TContext : DataContext

qui agit effectivement sur une instance d'une autre

public class MyOtherClass<T> : IEnumerable<T>

Je veux imposer que le TContext a un Table<T>. Existe-t-il un moyen propre de faire respecter cela?

Était-ce utile?

La solution

Voulez-vous vérifier que TContext a un membre qui est une table < T > ;? Si tel est le cas, le seul moyen de le faire est de définir une interface pour ce contrat et de modifier vos contraintes génériques

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

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

MODIFIER

Jason a posté un commentaire pour éclaircir ma réponse. Le nom Table n'est pas statique, mais dépend du type de T.

Si tel est le cas, il n’est pas possible de l’appliquer de manière statique via des contraintes génériques. Le mieux que vous puissiez faire est de créer une classe d'adaptateur qui implémente IMyTable & Lt; & Gt; et fournit un DataContext et une instance 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; } }
}

Autres conseils

Je pense que JaredPar a eu la bonne idée la première fois.

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(); 
  }
}

Je souhaite élargir sa réflexion en ajoutant une implémentation d'interface explicite. Cela répond à la remarque de Jason sur l'accès à la propriété table via IMyTable. Le type doit être impliqué d’une manière ou d’une autre et si vous avez un IMyTable<T>, le type est impliqué.

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>(); } }  
}

Maintenant, il est possible de faire ceci:

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

le seul moyen de l'appliquer est que si Table était dans une interface et que vous ayez attribué une contrainte générique ... donc quelque chose comme

public class MyOtherClass<T> : IEnumerable<T>, IHasTable<T>
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top