postgresql 实体框架核心 - 包含区分大小写还是不区分大小写?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/43277868/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-10-21 02:32:52  来源:igfitidea点击:

Entity Framework core - Contains is case sensitive or case insensitive?

c#databasepostgresqllinqentity-framework-core

提问by 001

"Contains" in Entity Framework core should equivalent to the SQL %like% operator. Therefore "Contains" should be case insensitive however it is case sensitive! (at least in postgres????)

实体框架核心中的“包含”应等效于 SQL %like% 运算符。因此“包含”应该不区分大小写,但它区分大小写!(至少在 postgres 中????)

The following only outputs a result when the correct casing for keyword is used.

以下仅在使用正确的关键字大小写时输出结果。

context.Counties.Where(x => x.Name.Contains(keyword)).ToList();

What am I doing wrong?

我究竟做错了什么?

回答by DarkUrse

It used to be the case for older versions of EF core. Now string.Containsis case sensitive, and for exemple for sqlite it maps to sqlite function `instr()' ( I don't know for postgresql).

旧版本的 EF 核心曾经是这种情况。现在string.Contains区分大小写,例如 sqlite 它映射到 sqlite 函数 `instr()'(我不知道 postgresql)。

If you want to compare strings in a case-insensitive way, you have DbFunctions to do the jobs.

如果您想以不区分大小写的方式比较字符串,您可以使用 DbFunctions 来完成这项工作。

context.Counties.Where(x => EF.Functions.Like(x.Name, $"%{keyword}%")).ToList();

UPDATE to @Gert:

更新到@Gert:

A part of the assumption in the question is incorrect. string.Containsdoes NOT convert into a LIKE expressioneven though it USED to be the case in ef core versions <= 1.0 (I think).

问题中的部分假设是不正确的。即使在 ef 核心版本 <= 1.0(我认为)中曾经是这种情况,string.Contains也不会转换为 a LIKE expression

  • In SQLServerstring.containsconverts into CHARINDEX(), in oracleand sqliteinto instr()which are case sensitive by default UNLESS db or column collation is defined otherwise ( Again, I don't know for postgresql ).
  • In all cases EF.Functions.Like()converts into a SQL LIKEexpression which is case-insensitive by default unless db or column collation is defined otherwise.
  • SQLServer的string.contains转换为CHARINDEX(),在预言源码instr()其是除非分贝或列排序规则定义,否则情况下,通过默认敏感(同样,我不知道对PostgreSQL)。
  • 在所有情况下,EF.Functions.Like()转换为LIKE默认情况下不区分大小写的 SQL表达式,除非另外定义了 db 或列排序规则。

So yes it all goes down to collation but - correct me if I'm wrong - in a way the code can have an influence on the case-sensitive/insensitive search depending on which one of the above method you use.

所以是的,这一切都归结为整理,但是 - 如果我错了,请纠正我 - 在某种程度上,代码可能会对区分大小写/不敏感的搜索产生影响,具体取决于您使用的上述方法之一。

Now, I might not be completely up to date but I don't think EF core migrations deal with DB collation naturally and unless you've already created the table manually you will end up with the default collation (case-sensitive for sqlite and I honestly don't know for the others).

现在,我可能还没有完全了解最新情况,但我认为 EF 核心迁移不会自然地处理 DB 排序规则,除非您已经手动创建了表,否则最终会使用默认排序规则(对 sqlite 和我区分大小写)老实说不知道其他人)。

Getting back to the original question you have at least 2 options to perform this case-insensitive search if not 3 in a future release :

回到最初的问题,您至少有 2 个选项来执行此不区分大小写的搜索,如果不是未来版本中的 3 个:

  1. Specify the column collation on creation using DbContext.OnModelCreating() using this trick
  2. Replace your string.Containsby EF.Functions.Like()
  3. Or wait for a promising feature still in discussion: EF.Functions.Collate()function
  1. 使用此技巧使用 DbContext.OnModelCreating() 在创建时指定列排序规则
  2. 替换你string.ContainsEF.Functions.Like()
  3. 或者等待一个仍在讨论中的有前途的功能:EF.Functions.Collate()功能

回答by Stas Boyarincev

My answer will concern NpgSQL.

我的回答将涉及 NpgSQL。

  1. EF.Functions.Like()in PostgreSQL is case-sensitive, but you can use EF.Functions.ILike()extension methodlocated in Npgsql.EntityFrameworkCore.PostgreSQLassembly.

  2. If you don't have reference to Entity Framework assembly in place where you build query, you can use combination ToLower()and Contains()methods, because Npgsql is abletranslate ToLower()method to correct SQL

  1. EF.Functions.Like()在 PostgreSQL 中区分大小写,但您可以使用位于assembly 中的EF.Functions.ILike()扩展方法Npgsql.EntityFrameworkCore.PostgreSQL

  2. 如果您在构建查询的地方没有引用实体框架程序集,您可以使用组合ToLower()Contains()方法,因为 Npgsql能够转换ToLower()方法来纠正 SQL

Example:

例子:

context.Counties.Where(x => x.Name.ToLower().Contains(keyword.ToLower())).ToList();

About second method keep in mind: you may have performance problems and may encounter problems associated with encoding.

关于第二种方法,请记住:您可能会遇到性能问题,并且可能会遇到与编码相关的问题。

回答by Kfir Guy

IQueryable.Whereis executed in the database, so it is most likely to be case insensitive.

IQueryable.Where在数据库中执行,因此很可能不区分大小写。

IEnumerable.Whereuses C# String.Contains, so it is case sensitive.

IEnumerable.Where使用 C# String.Contains,因此区分大小写。

Read this answer: Returning IEnumerable vs. IQueryable

阅读此答案:返回 IEnumerable 与 IQueryable

回答by topcool

Just try it :

去尝试一下 :

You can Lower casefield and search value

您可以Lower case字段和搜索值

  context.Counties.Where(x => x.Name.ToLower().Contains(keyword.ToLower())).ToList();

Or you can Upper Casefiled and search value

或者您可以Upper Case归档并搜索值

context.Counties.Where(x => x.Name.ToUpper().Contains(keyword.ToUpper())).ToList();