站点图标 江湖人士

Entity Framework Core Like 查询揭秘

  提示:在做一些示例演示时,个人喜欢会用 Xunit + Resharper,这样可以直接运行对应的示例,并且也可以直接输出对应的结果。

  您肯定在Entity Framework中使用过这些方式,我们还是简单说明一下这三个方法的作用:

  在这里我只列举了Contains的示例,StartsWith和EndsWith的功能非常相似,我就不重复列举了。

  这两个示例的运行结果是一致的,那么微软为什么要提供EF.Functions.Like()方法呢?

  我们知道在 T-SQL 语句中Like关键字支持通配符,下面简单介绍支持的通配符:

  我们的将查询关键字由“t”改为“[a-c]”,再来看上面两个示例分别运行的结果:

  上面运行的结果,Like查询的结果返回三条记录,而Contains查询的结果无任何数据返回。

  通过上面示例以及捕获的SQL,我们可以得知,EF.Functions.Like() 查询会被解释成为 Like,实际上是查询字符串中包括“a”、“b”、“c”这三个字符中任何一个字符的数据,而使用 Contains 查询会被解析成为 CharIndex 函数,实际是指查询字符串中包括“[a-c]”的字符串。

  提示:StartsWith和EndsWith分别会被解析成为Left和Right函数,测试结果在这里不再做重复演示。

  如果使用StartWith方法来实现模糊查询,解析后的SQL语句会包括一个Like查询,您可能要说,刚才不是已经讲过吗,StartsWith、Contains和EndsWith方法解析后的SQL不是通过 Like 来查询!先不要着急,我下面来说清楚这个问题。

  您可能知道在数据库查询时,如果在某一个字段上使用函数是无法利用到索引的;在使用Left,CharIndex和Right时是无法利用到索引的;而Like查询在百分号后置的情况下会利用到索引。关于数据库的这些知识,在博客园上有很多文章,我就不重复说明了。

  结论:StartsWith模糊查询解析后的SQL用到Like,这是因为Like在百分号后置的是情况下会利用到索引,这样查询速度会更快。Contains和EndsWith模糊查询解析后的SQL不包括Like查询,因为在分百号前置的情况无法引用到索引。

  关于Contains和EndsWith模糊查询的测试,在这里不再重复,您可以自己测试。

  在EF 6中,模糊查询解析后的SQL语句与EF Core中略有不同,但是执行的结果没有区别。

  StartsWith、Contains和EndsWith方法均会被解析为Like查询,但是是传递的参数由:“[a-c]”变为了“~[a-b]”,前面多了一个特殊符号“~”,并且查询子句的后面还多了一部分ESCAPE N~。

  搜索包含一个或多个特殊通配符的字符串。 例如,customers 数据库中的 discounts 表可能存储含百分号 (%) 的折扣值。 若要搜索作为字符而不是通配符的百分号,必须提供 ESCAPE 关键字和转义符。 例如,一个样本数据库包含名为 comment 的列,该列含文本 30%。 若要搜索在 comment 列中的任何位置包含字符串 30% 的任何行,请指定 WHERE comment LIKE %30!%% ESCAPE ! 之类的 WHERE 子句。 如果未指定 ESCAPE 和转义符,则数据库引擎将返回包含字符串 30 的所有行。

  如果您想了解EF 6是如果过滤这些通配符的,可以在Github上面了解,链接地址:。

  结论:在EF 6中StartsWith、Contains和EndsWith方法均会被解析为Like查询,但是如果出现了通配符,框架会结合ESCAPE以及自身过滤功能将参数进行转义。

  在EF Core中StartsWith模糊查询解析后的SQL用到Like,这是因为Like在百分号后置的是情况下会利用到索引,这样查询速度会更快;

  在EF 6中,StartsWith、Contains和EndsWith方法均会被解析为Like查询,但是如果出现了通配符,框架会结合ESCAPE以及自身过滤功能将参数进行转义;

  在EF 6中,模糊查询不支持通配符,在这一点是因为我没有找到对应的解决方案,如果您知道,请留言,谢谢!

退出移动版