c# - new - Dynamic LINQ-¿Hay una versión.NET 4?
named tuples c# (4)
Estoy buscando utilizar LINQ para algunas rutinas de búsqueda y quería tener algunas cláusulas dinámicas where. Entonces, por ejemplo, si un usuario desea buscar por ciudad o buscar por estado, tendría una llamada dinámica LINQ Where <> en lugar de crear dos expresiones LINQ fuertemente tipadas y luego usar la apropiada en función de cómo el usuario desea buscar .
Entonces me gustaría hacer esto:
String criteria="p.City=''Pittsburgh''"; //or "p.State=''PA''"
personData.Where(criteria)
en lugar de
personData.Where(p => p.City=="Pittsburgh");
o
personData.Where(p => p.State=="PA");
Encontré una publicación de blog de Scott Guthrie hablando de Dynamic LINQ en las muestras de Visual Studio 2008. Esto parece hacer lo que quiero, pero mis preguntas son:
- ¿Esta biblioteca de muestra es compatible con Microsoft?
- El artículo de Scott Guthrie se refiere a VS2008 (.NET 3.5). ¿Hay una mejor opción para .NET 4? Tal vez algo que fue lanzado con .NET 4 que logra lo mismo (o algo muy cercano)?
¡Gracias por adelantado!
Ahora debería estar disponible. Podría descargarlo a través de NuGet: http://www.nuget.org/packages/System.Linq.Dynamic/
Es posible que desee echar un vistazo a PredicateBuilder
Esta característica sería muy agradable de tener. Una característica similar existe en ADO.net Datatables . Sería de gran ayuda para LinqToSql también. Seguro que perdería una verificación fuertemente tipada, pero ese es el punto, desea búsquedas dinámicas. Si manejas las excepciones correctamente, realmente creo que es una característica que vale la pena tener.
Puede considerar agregar una solicitud de función a Microsoft Connect . La biblioteca ya existe tal vez considerarán agregar soporte oficial para ella. Si realiza una solicitud de función, asegúrese de publicar un enlace aquí para que podamos votar. Microsoft Connect tiene un sistema de votación similar al . He enviado algunas LinqtoSql TableUpdate y VB.net Readonly Interfaces como C # .
Recuerdo que tuve algunos problemas con esta biblioteca. Creo que tiene algo que ver con los métodos estáticos.
Me pareció mejor desarrollar las expresiones que necesitaba. Este codeproject.com/KB/aspnet/AspNetMVCandJqGrid.aspx de Ilya Builuk demuestra expresiones personalizadas. Lo bueno del marco de trabajo de Ilya es que elimina gran parte del código repetitivo al hacer operaciones como ordenar jqGrid.
Lo encontré extremadamente útil cuando aprendí sobre los conceptos subyacentes de las expresiones.
Lo bueno de este código es que te permite usar operadores de puntos para getters. Person.Age
o si quieres violar Demeter incluso puedes hacer múltiples getters.
El código puede mejorarse. Creo que agregué StartsWith
y solo lo StartsWith
para operaciones de cadena así como para algunas otras operaciones de búsqueda. A pesar de que vale la pena mirar, me ayudó a entender mucho las expresiones de linq.
public static IQueryable<T> Where<T>(this IQueryable<T> query, string column, object value, WhereOperation operation)
{
if (string.IsNullOrEmpty(column))
return query;
ParameterExpression parameter = Expression.Parameter(query.ElementType, "p");
MemberExpression memberAccess = null;
foreach (var property in column.Split(''.''))
memberAccess = MemberExpression.Property
(memberAccess ?? (parameter as Expression), property);
//change param value type
//necessary to getting bool from string
ConstantExpression filter = Expression.Constant
(
Convert.ChangeType(value, memberAccess.Type)
);
//switch operation
Expression condition = null;
LambdaExpression lambda = null;
switch (operation)
{
//equal ==
case WhereOperation.Equal:
condition = Expression.Equal(memberAccess, filter);
lambda = Expression.Lambda(condition, parameter);
break;
//not equal !=
case WhereOperation.NotEqual:
condition = Expression.NotEqual(memberAccess, filter);
lambda = Expression.Lambda(condition, parameter);
break;
//string.Contains()
case WhereOperation.Contains:
condition = Expression.Call(memberAccess,
typeof(string).GetMethod("Contains"),
Expression.Constant(value));
lambda = Expression.Lambda(condition, parameter);
break;
}
MethodCallExpression result = Expression.Call(
typeof(Queryable), "Where",
new[] { query.ElementType },
query.Expression,
lambda);
return query.Provider.CreateQuery<T>(result);
}
Enumerador de WhereOperation:
public enum WhereOperation { Equal, NotEqual, Contains }
No creo que sea "compatible" con Microsoft, parece ser lanzado bajo una licencia pública, que dice en parte:
(E) El software tiene licencia "tal como está". Usted corre el riesgo de usarlo. Los colaboradores no dan garantías expresas, garantías o condiciones. Es posible que tenga derechos adicionales del consumidor bajo sus leyes locales que esta licencia no puede cambiar. En la medida permitida por sus leyes locales, los contribuyentes excluyen las garantías implícitas de comerciabilidad, idoneidad para un propósito particular y no infracción.
En su segunda pregunta, no creo que haya una versión .NET 4. El 3.5 debería funcionar bien en un proyecto de 4.0, y no creo que haya mucho que agregar. Según tengo entendido, esta era una biblioteca pequeña e ingeniosa para hacer esas ocasionales consultas de linq basadas en cadenas. Tal vez, por alguna razón, ordenó manualmente una cuadrícula y necesitó modificar el orden de clasificación de las colecciones en función de una cadena que representa la propiedad en cuestión. Voila. Dudo que veas un gran esfuerzo poner muchas características en esto.