ASP.NET MVC3アプリケーションをC#で開発しています。
検索で取得した結果セットを適用する「絞り込み」機能をアプリケーションに実装しようとしています。
つまり、検索を実行してページの中央に結果を表示した後、ページの左側/右側に、検索結果の各プロパティの CheckBoxList
ヘルパーを配置したいと考えていCheckBoxList
。 CheckBox
それぞれのCheckBoxList
プロパティの異なる値を表します。
たとえば、 Product
を検索し、値がblue、red 、 yellowの Color
プロパティがある場合、テキストColorと各色に1つずつ、3つのCheckBox
-esを持つCheckBoxList
を作成しCheckBoxList
。
Webでの調査の結果、Scott Guthrieが提供するこの動的LINQライブラリが見つかりました。私が見つけた最新の例/チュートリアルは2009年のものなので、このライブラリが実際に良い(そして維持されている)かどうか疑問に思っていました。
後者の場合、 jQueryはそのような機能を実装する最良の方法ですか?
純粋な.NETフレームワークを使用して、必要な述語式を動的に構築することで、問題を解決できます。
以下のコードサンプルを参照してください。基準に応じて、これは複数のプロパティでフィルタリングします。エンティティフレームワークなどのリモートシナリオとしてインメモリの両方を有効にするため、IQuerableを使用しました。 Entity Frameworkを使用している場合は、EntitySQL文字列を動的に作成することもできます。私はそれがより良いパフォーマンスを期待します。
関係するリフレクションの一部(GetProperty)があります。ただし、BuildPredicateメソッド内でキャッシュを実行することで、これを改善できます。
public class Item
{
public string Color { get; set; }
public int Value { get; set; }
public string Category { get; set; }
}
class Program
{
static void Main(string[] args)
{
var list = new List<Item>()
{
new Item (){ Category = "Big", Color = "Blue", Value = 5 },
new Item (){ Category = "Small", Color = "Red", Value = 5 },
new Item (){ Category = "Big", Color = "Green", Value = 6 },
};
var criteria = new Dictionary<string, object>();
criteria["Category"] = "Big";
criteria["Value"] = 5;
var query = DoDynamicWhere(list.AsQueryable(), criteria);
var result = query.ToList();
}
static IQueryable<T> DoDynamicWhere<T>(IQueryable<T> list, Dictionary<string, object> criteria)
{
var temp = list;
//create a predicate for each supplied criterium and filter on it.
foreach (var key in criteria.Keys)
{
temp = temp.Where(BuildPredicate<T>(key, criteria[key]));
}
return temp;
}
//Create i.<prop> == <value> dynamically
static Expression<Func<TType, bool>> BuildPredicate<TType>(string property, object value)
{
var itemParameter = Expression.Parameter(typeof(TType), "i");
var expression = Expression.Lambda<Func<TType, bool>>(
Expression.Equal(
Expression.MakeMemberAccess(
itemParameter,
typeof(TType).GetProperty(property)),
Expression.Constant(value)
),
itemParameter);
return expression;
}
}