2009-07-24 10 views
0

Qu'est-ce que j'écris au lieu de ??????? sélectionner la surcharge appropriée?Comment faire référence à une surcharge non générique correcte dans C#?

using System; 
using System.Collections.Generic; 

namespace ConsoleApplication2 
{ 
    class A {} 

    class B : A {} 

    class C : A {} 

    class Program 
    { 
     static void Main(string[] args) 
     { 
      var l1 = new List<C>(); 
      var l2 = new List<C>(); 
      Comparer<C>(l1, l2, ???????); 
     } 

     void Compare(C a, C b) { } 

     void Compare(B a, B b) {} 

     void Compare<T>(IList<T> a, IList<T> b, Action<T,T> comparator) 
     { 
      for (int i = 0; i < a.Count; i++) 
       comparator(a[i], b[i]); 
     } 
    } 
} 

Répondre

5

Vous avez juste besoin de rendre les méthodes statiques et de corriger le nom de la méthode. Vous pouvez même utiliser l'inférence de type sur l'appel initial à Compare:

static void Main(string[] args) 
{ 
    var l1 = new List<C>(); 
    var l2 = new List<C>(); 

    Compare(l1, l2, Compare); 
} 

static void Compare(C a, C b) {} 

static void Compare(B a, B b) {} 

static void Compare<T>(IList<T> a, IList<T> b, Action<T,T> comparator) 
{ 
    for (int i = 0; i < a.Count; i++) 
     comparator(a[i], b[i]); 
} 

Dans ce cas, il n'y a pas d'ambiguïté - Compare(C, C) est la seule méthode dans le groupe qui est convertible à un Action<C, C>. Si vous aviez une méthode Compare(A, A), la méthode la plus spécifique serait toujours sélectionnée. Vous obtiendrez l'ambiguïté si au lieu que vous aviez:

static void Compare(A a, C b) {} 
static void Compare(C a, A b) {} 

Cependant, je fortement recommande que dans les cas comme celui-ci vous essayez d'éviter de surcharger la mesure du possible. Donnez aux méthodes des noms distincts - cela rendra la lecture beaucoup plus facile et évitera toute ambiguïté.

+0

Merci, mon mauvais! – UserControl

0

Cela dépend de ce que vous voulez faire avec les valeurs. Si vous voulez juste passer un délégué, vous pouvez effectuer les opérations suivantes

Comparer<C>(l1,l2, (left,right) => {}); 

Dans ce cas, la partie C < > peut effectivement être laissé. Le compilateur sera capable de déduire les paramètres.

Je suis curieux au sujet de votre choix de Action<T,T> pour le paramètre nommé. Les fonctions de comparaison renvoient généralement une valeur qui représente le résultat de la comparaison de deux valeurs. Le type Action<T,T> renvoie juste la valeur vide. Il devrait probablement être soit

  1. changé à Func<T,T,int> qui est une signature plus standard pour une fonction de comparaison
  2. Modifier le nom du paramètre à quelque chose de plus indicitive d'une fonction qui ne renvoie pas une valeur. Comme del, action ou func.
Questions connexes