首先要做的是开启日志记录,以查看生成的TSQL语句;例如:
ctx.Log = Console.Out
LINQ-to-SQL 似乎在处理 null 值方面有点不一致(取决于字面值还是实际值):
using(var ctx = new DataClasses2DataContext())
{
ctx.Log = Console.Out;
int? mgr = (int?)null;
var bosses1 = ctx.Employees.Where(x => x.ReportsTo == (int?)null).ToList();
var bosses2 = ctx.Employees.Where(x => x.ReportsTo == mgr).ToList();
}
所以我能建议的就是使用带有空值的顶部表单!
即:
Expression<Func<Category,bool>> predicate;
if(categoryId == null) {
predicate = c=>c.ParentId == null;
} else {
predicate = c=>c.ParentId == categoryId;
}
var subCategories = this.Repository.Categories
.Where(predicate).ToList().Cast<ICategory>();
更新-我使用一个自定义的“表达式”将其“正确地”运行:
static void Main()
{
ShowEmps(29);
ShowEmps(null);
}
static void ShowEmps(int? manager)
{
using (var ctx = new DataClasses2DataContext())
{
ctx.Log = Console.Out;
var emps = ctx.Employees.Where(x => x.ReportsTo, manager).ToList();
Console.WriteLine(emps.Count);
}
}
static IQueryable<T> Where<T, TValue>(
this IQueryable<T> source,
Expression<Func<T, TValue?>> selector,
TValue? value) where TValue : struct
{
var param = Expression.Parameter(typeof (T), "x");
var member = Expression.Invoke(selector, param);
var body = Expression.Equal(
member, Expression.Constant(value, typeof (TValue?)));
var lambda = Expression.Lambda<Func<T,bool>>(body, param);
return source.Where(lambda);
}