2013-10-26 51 views
15

基础上回答了这个问题:不区分大小写的字符串比较在C#中不起作用?

How can I do a case insensitive string comparison?

我试图做一个区分大小写的比较不使用比较或ToLower将:

var user = db.Users.FirstOrDefault(s => String.Equals(s.Username, username, StringComparison.OrdinalIgnoreCase)); 

但是我得到一个错误:

Incorrect number of arguments supplied for call to method 'Boolean Equals(System.String, System.String, System.StringComparison)'

我在做什么错?

+0

你有没有验证用户名和s.Username都是字符串类型的。 – Tilak

+1

很确定L2S不支持这种特殊的方法。如果这是实际的可执行C#代码,而不是查询提供程序翻译的东西,那就好了。 – Servy

+0

你为什么要避免使用string.Compare? – tsells

回答

33

StringComparison.OrdinalIgnoreCase的字符串比较在内存中或与IEnumerable<T>一起使用。您正试图与IQueryable<T>一起使用它,但您的查询的提供者不理解它。

在LINQ到SQL,你应该能够使用SqlMethods.Like(s.UserName, userName),像这样:

var user = db.Users.FirstOrDefault(s => SqlMethods.Like(s.UserName, userName)); 

SqlMethods在System.Data.Linq.SqlClient命名空间。

Like方法是不区分大小写的,所以你应该得到预期的结果。

EDIT : I tried and get "LINQ to Entities does not recognize the method Boolean Like(System.String, System.String) method, and this method cannot be translated into a store expression."

这似乎是EF的一个已知问题(link)。

This works for me:

db.Users.FirstOrDefault(
    s => s.Username.Equals(username, StringComparison.OrdinalIgnoreCase) 
); 

看来,虽然英孚已经很难翻译的静态Equals到SQL,它没有任何问题翻译实例Equals。这是一个很好的发现 - 它使得易于阅读,高性能的解决方案成为可能。

你也可以用一个简单的方法与ToUpperCaseToLowerCase,但可能会阻止查询优化使用索引:

// Warning: this may not perform well. 
var user = db.Users.FirstOrDefault(s => s.UserName.ToUpperCase() == userName.ToUpperCase()); 
+1

谢谢你。我尝试并得到“LINQ to Entities无法识别该方法”布尔Like(System.String,System.String)'方法,并且此方法无法转换为商店表达式。“ - 想法? – SB2055

+0

这适用于我:db.Users.FirstOrDefault(s => s.Username.Equals(username,StringComparison.OrdinalIgnoreCase));我不知道如何选择答案 - 请随时注意这一点,我可以检查你的答案吗? – SB2055

+0

你会说我在评论中发布的解决方案有什么问题吗?我一直在寻找一种遵循最佳实践的简单,高性能的解决方案。 – SB2055

相关问题