2009-06-08 24 views
5

Me gustaría poder pasar un Func < T,? > que me permite elegir exactamente cómo ordenar una lista de elementos ... el problema que tengo es que el tipo de devolución puede variar ... así que por ejemplo quiero hacer algo como esto (no código de producción):¿Función de pedido genérico Linq?

Func<POline, string> poLineOrder 
if (option) poLineOrder = poline => poline.PartNumber; 
else poLineOrder = poline => poline.LineOrder; 
var orderedLines = poLines.OrderBy(poLineOrder); 

El problema aquí es que mientras PartNumber es una cadena, LineOrder es una int, y este código no se compila. Tengo la sensación de que voy a tener que crear una Expresión (?) Pero parece que no puedo obtener la sintaxis correcta.

(Sí, puedo solucionar esto, mediante el uso de poline.LineOrder.ToString ("D10") pero yo estoy haciendo la pregunta más general aquí ... gracias!)

-mdb

Respuesta

5

OrderBy espera un selector de funciones clave de tipo Func<Item, Key> y un opcional IComparer<Key> para definir la comparación en sí.

que necesitará las siguientes definiciones: ayudante

class FunctorComparer<T> : IComparer<T> { 
     private readonly Comparison<T> m_Comparison; 

     public FunctorComparer(Comparison<T> Comparison) { 
      this.m_Comparison = Comparison; 
     } 

     public int Compare(T x, T y) { 
      return m_Comparison(x, y); 
     } 
    } 

    static Comparison<TKey> Compare<TKey, TRes>(Func<TKey, TRes> Selector) where TRes : IComparable<TRes> { 
     return (x, y) => Selector(x).CompareTo(Selector(y)); 
    } 

Ahora se puede escribir

Comparison<POLine> x; 

if (option) 
    x = Compare<POLine, int>(l => l.PartNumber); 
else 
    x = Compare<POLine, string>(l => l.LineOrder); 

var res = poLines.OrderBy(i => i, new FunctorComparer<POLine>(x)); 
3

Es posible que desee considerar el uso de Dynamic LINQ del VS2008 Samples. A continuación, puede hacer:

var orderedLines = poLines.OrderBy(poLineOrder ? "PartNumber" : "LineOrder"); 
+0

Atención a comentar sobre el downvote? – tvanfosson

+0

@tvanfosson, recibí el mismo tratamiento para un enfoque diferente pero válido. Parece que alguien solo quería renunciar :( – JaredPar

Cuestiones relacionadas