2016-07-04 6 views
0

私はLINQというクエリを次のように書いていますが、より一般的なものにしてハードコーディングされた値を取り除くことができるかどうかは疑問です。LINQ作成orderbydesc generic

switch (sortOrder) 
{ 
    case "DESC": 
     if(sortBy == "A") 
      query = query.OrderByDescending(x => x.Field1); 
     if(sortBy == "B") 
      query = query.OrderByDescending(x => x.Field2); 
     if (sortBy == "C") 
      query = query.OrderByDescending(x => x.Field3); 
     break; 
    default: 
     if(sortBy == "A") 
      query = query.OrderBy(x => x.Field1); 
     if(sortBy == "B") 
      query = query.OrderBy(x => x.Field2); 
     if (sortBy == "C") 
      query = query.OrderBy(x => x.Field3); 
     break; 
} 

私が探しているのは答えではありません。その質問では、ユーザはASCの1番目をソートしてDescを尋ねました。

私の場合、私はASCかDESCのどちらかをソートする必要があります。

+1

これまで実行を制御するために、 'string'sを使用しないでくださいあなたは、あなたがそれをTSourceのプロパティを選択して式を与える、すなわち、標準OrderBy()のようにそれを使うだろう。 'bool'フラグ、' enum'、あるいはより良い多態性を使用してください。 –

+0

'sortBy'変数は誰が設定しますか?それはユーザーによって選択され、このコードに渡されますか? –

答えて

2

あなただけリフレクションを使用すると、私は推測することを行うことができます。

static IEnumerable<T> Order<T, V>(IEnumerable<T> query, string sortOrder, 
            Func<T, V> fieldSelector) 
{ 
    string methodName = sortOrder == "DESC" ? "OrderByDescending" : "OrderBy"; 
    MethodInfo method = typeof(Enumerable).GetMethods() 
              .Where(x => x.Name.Contains(methodName)) 
              .FirstOrDefault(); 

    MethodInfo genericMethod = method.MakeGenericMethod(typeof(Resource), typeof(V)); 

    var orderedResults = (IEnumerable<T>)genericMethod.Invoke(null, 
            new object[] { query, fieldSelector }); 

    return orderedResults; 
} 

使用法:

var orderdResults = Order(query, "DESC", x => x.CategoryId).ToList(); 
+0

フォーマットを垂直にスクロールせずに読むことができるように修正してください。また、これは 'IQueryable'のためには機能しません。つまり、Entity Frameworkでは動作しません。 'fieldSelector'は'式> 'でなければなりません。 –

0

を使用すると、LINQのOrderBy()を再実装する理由私は得ることはありませんが、これはあります最も賢明な方法は、それを行うには、私が推測する:

public static class Extensions 
{ 
    public static IOrderedQueryable<TSource> Order<TSource, TKey>(
     this IQueryable<TSource> source, 
     Expression<Func<TSource, TKey>> keySelector, 
     bool descending = false) 
    { 
     return descending 
      ? source.OrderByDescending(keySelector) 
      : source.OrderBy(keySelector); 
    } 
} 
var newest = query.Order(x => x.Id, true).First(); 
var oldest = query.Order(x => x.Id).First(); 

Workinge例:https://dotnetfiddle.net/TcEEqY