To nie jest porównanie z rozróżnianiem wielkości liter w LINQ to Entities:
Thingies.First(t => t.Name == "ThingamaBob");
Jak mogę uzyskać porównanie z rozróżnianiem wielkości liter w LINQ to Entities?
c#
.net
entity-framework-4
linq-to-entities
Ronnie Overby
źródło
źródło
Odpowiedzi:
Dzieje się tak, ponieważ używasz LINQ To Entities, które ostatecznie konwertuje twoje wyrażenia Lambda na instrukcje SQL. Oznacza to, że rozróżnianie wielkości liter zależy od serwera SQL Server, który domyślnie ma sortowanie SQL_Latin1_General_CP1_CI_AS i NIE rozróżnia wielkości liter.
Użycie ObjectQuery.ToTraceString do zobaczenia wygenerowanego zapytania SQL, które zostało faktycznie przesłane do SQL Server, ujawnia tajemnicę:
Podczas tworzenia LINQ podmiotom kwerendy LINQ do podmiotów wykorzystuje parser LINQ, aby rozpocząć przetwarzanie zapytań i zamienia go na drzewie wyrażenie LINQ. Drzewo wyrażeń LINQ jest następnie przesyłane do interfejsu API usług obiektów , które konwertuje drzewo wyrażeń na drzewo poleceń. Następnie jest wysyłany do dostawcy sklepu (np. SqlClient), który konwertuje drzewo poleceń na tekst polecenia natywnej bazy danych. Zapytanie jest wykonywane w magazynie danych, a wyniki są materializowane w obiektach jednostek przez usługi obiektowe. Nie wprowadzono żadnej logiki, aby uwzględnić rozróżnianie wielkości liter. Więc bez względu na to, jaki przypadek umieścisz w swoim predykacie, będzie on zawsze traktowany jako taki sam przez serwer SQL Server, chyba że zmienisz sortowanie SQL Server dla tej kolumny.
Rozwiązanie po stronie serwera:
Dlatego najlepszym rozwiązaniem byłaby zmiana sortowania kolumny Name w tabeli Thingies na COLLATE Latin1_General_CS_AS, w której rozróżniana jest wielkość liter, uruchamiając to na serwerze SQL:
Aby uzyskać więcej informacji na temat SQL Server zestawia podjąć aa spojrzenie na SQL Server Sortowanie Case Sensitive SQL Query Szukaj
Rozwiązanie po stronie klienta:
Jedynym rozwiązaniem, które możesz zastosować po stronie klienta, jest użycie LINQ to Objects do wykonania kolejnego porównania, które nie wydaje się zbyt eleganckie:
źródło
Możesz dodać adnotację [CaseSensitive] dla EF6 + Code-first
Dodaj te zajęcia
Zmodyfikuj swój DbContext, dodaj
Więc zrób
Add-Migration CaseSensitive
Zaktualizować bazę danych
na podstawie artykułu https://milinaudara.wordpress.com/2015/02/04/case-sensitive-search-using-entity-framework-with-custom-annotation/ z poprawką błędów
źródło
WHERE
warunki w SQL Server domyślnie nie uwzględniają wielkości liter. Uwzględnij wielkość liter, zmieniając domyślne sortowanie kolumny (SQL_Latin1_General_CP1_CI_AS
) naSQL_Latin1_General_CP1_CS_AS
.Kruchym sposobem na to jest użycie kodu. Dodaj nowy plik migracji, a następnie dodaj to wewnątrz
Up
metody:Ale
Możesz utworzyć niestandardową adnotację o nazwie „Uwzględnianie wielkości liter” za pomocą nowych funkcji EF6 i ozdobić swoje właściwości w następujący sposób:
Ten wpis na blogu wyjaśnia, jak to zrobić.
źródło
Odpowiedź udzielona przez @Morteza Manavi rozwiązuje problem. Mimo to, dla rozwiązania po stronie klienta , elegancki sposób byłby następujący (dodanie podwójnego sprawdzenia).
źródło
Podobała mi się odpowiedź Morteza i normalnie wolałbym to naprawić po stronie serwera. Po stronie klienta zwykle używam:
Zasadniczo najpierw sprawdź, czy jest użytkownik z wymaganymi kryteriami, a następnie sprawdź, czy hasło jest takie samo. Trochę rozwlekły, ale wydaje mi się, że jest łatwiejszy do odczytania, gdy w grę wchodzi cała masa kryteriów.
źródło
Żaden z nich nie
StringComparison.IgnoreCase
działał dla mnie. Ale to zrobiło:źródło
How can I achieve case sensitive comparison
Użyj string.Equals
Nie musisz też martwić się o wartość null i odzyskać tylko potrzebne informacje.
Użyj StringComparision.CurrentCultureIgnoreCase dla bez uwzględniania wielkości liter.
źródło
Nie jestem pewien co do EF4, ale EF5 obsługuje to:
źródło
StringComparison
wyliczenia, aby coś zmienić. Widziałem wystarczająco dużo osób sugerujących, że tego rodzaju rzeczy powinny działać, aby pomyśleć, że problem jest gdzieś w pliku EDMX (db-first), chociaż stackoverflow.com/questions/841226/ ...