我正在尝试针对EF实体类型(人)创建常规搜索查询。通常,搜索采用字符串,用逗号分隔,然后搜索各种属性包含所有关键字的人。
我有一个名为getProperties(Person p)的函数,它接受一个实体(由实体类型覆盖),并返回一个用分隔符连接在一起的各种相关属性的字符串......例如:
John~Doe~Team A~Full Time
如果用户搜索“Team A,Full”,则应返回与上述展平实体相对应的人...但是,如果输入“John,Smith”则不应该返回。
我认为以下情况看起来正确,但它不起作用......
public IEnumerable<Person> SearchPeople(string searchString)
{
if (searchString == null || string.IsNullOrEmpty(searchString.Trim()))
return base._objectSet.ToList();
string[] SearchWords = searchString.Split(',').Select(s => s.Trim()).ToArray();
return (from person
in base._objectSet
let t = (getProperties(person))
where SearchWords.All(word => t.Contains(word))
select person).ToList();
}
并且getProperties函数是:
public static string getProperties(Person p)
{
string[] values = { p.Surname, p.GivenName, p.Team, p.Status };
return values.Aggregate((x, y) => String.IsNullOrEmpty(y) ? x : string.Concat(x, "~", y));
}
有谁知道我哪里出错了?
修改
没有引发异常,但是当我单步执行代码时,当我到达linq时,它会进入托管查询的unitofwork的dispose方法。很奇怪。
如果我更改它以便搜索硬编码的字符串,它会按预期工作:
var test = (from person
in base._objectSet
where SearchWords.All(word => "John~Doe~Team A~Full Time".Contains(word))
select person).ToList();
嗯,它的作用是它匹配我期望的查询,但因为它是静态的,它返回每个人的记录(非常像在哪里(true)= P)
编辑第二个
甚至更奇怪的是,如果我将结果存储到var中,然后在返回时返回带有断点的var,执行永远不会到达断点...这个linq就像一个黑洞...我可以进入它,但它永远不会让我回到我的SearchPeople方法......它只是处理上下文并忘记它。
编辑第三个
如果我不立即调用ToString()并查看调试器中的linq表达式,它会说“Linq to Entities无法识别方法getProperties(Person)”看起来它在我的方法上默默地窒息..任何方式使用我的方法没有linq choking它?
答案 0 :(得分:0)
您要退回一份清单吗?尝试将返回类型设为列表或将.ToList()
更改为AsEnumerable()
public List<Person> SearchPeople(string searchString)
{
if (searchString == null || string.IsNullOrEmpty(searchString.Trim()))
return base._objectSet.ToList();
string[] SearchWords = searchString.Split(',').Select(s => s.Trim()).ToArray();
return (from person
in base._objectSet
let t = (getProperties(person))
where SearchWords.All(word => t.Contains(word))
select person).ToList();
}
答案 1 :(得分:0)
好吧,在发现linq 2 entites不喜欢方法之后(因为不知道如何将它翻译成sql),我重写了我的linq是一种非常乏味但功能正常的方式:
var people = from p
in base._objectSet
where SearchWords.All(p.GivenName.Contains(word) || p.Surname.Contains(word) || p.(???).Contains(word) || etc.)
select p;
烦人,但你去了。