복붙노트

[SQL] 대소 문자 구분 문자열은 LINQ - 투 - SQL에 비교

SQL

대소 문자 구분 문자열은 LINQ - 투 - SQL에 비교

나는 그것이 대소 문자가 구분되지 않는 문자열 비교를 수행의 ToUpper 및 ToLower는을 사용하는 것이 현명 읽었습니다, 그러나 LINQ - 투 - SQL에 올 때 나는 대안을 볼 수 없습니다. String.Compare의하여 ignoreCase 및 CompareOptions 인수 LINQ - 투 - SQL을 무시 (당신이 대소 문자를 구분하는 데이터베이스를 사용하는 경우, 당신은 당신이 대소 문자를 구분 비교를 요청할 경우에도 대소 문자를 구분 비교를 얻을). ToLower는 또는의 ToUpper 최선의 선택은 여기인가? 하나가 다른 것보다 더 나은가요? 나는의 ToUpper 더 나은 것을 선가 생각하지만 여기에 적용 나도 몰라. (I 코드 리뷰를 많이하고있어 모두가 ToLower는을 사용하고 있습니다.)

Dim s = From row In context.Table Where String.Compare(row.Name, "test", StringComparison.InvariantCultureIgnoreCase) = 0

이것은 단순히 "테스트"로 row.Name을 비교하고 대소 문자를 구분하는 데이터베이스에 "테스트"와 "TEST"를 반환하지 않습니다 SQL 질의로 변환된다.

해결법

  1. ==============================

    1.당신이 말하는 것처럼,의 ToUpper 및 ToLower는 사이에 몇 가지 중요한 차이가있다, 당신은 대소 문자를 구분 평등 검사를 수행하려고 할 때 단 하나의 안정적인 정확합니다.

    당신이 말하는 것처럼,의 ToUpper 및 ToLower는 사이에 몇 가지 중요한 차이가있다, 당신은 대소 문자를 구분 평등 검사를 수행하려고 할 때 단 하나의 안정적인 정확합니다.

    이상적으로, 대소 문자를 구별하지 평등 검사를 할 수있는 가장 좋은 방법은 다음과 같습니다

    String.Equals(row.Name, "test", StringComparison.OrdinalIgnoreCase)
    

    참고 그러나이이 경우에 작동하지 않습니다! 따라서 우리의 ToUpper 또는 ToLower는 함께 붙어있다.

    이 보안 안전 확인하기 위해 OrdinalIgnoreCase를합니다. 그러나 (에서) 사건의 정확한 종류는 사용하는 민감한 검사는 당신의 목적이 무엇인지에 따라 달라집니다. 그러나 일반적으로 사용 평등 검사에 같음하고 정렬 할 때 비교 한 다음 작업에 적합한 StringComparison을 선택합니다.

    마이클 카플란 (문화와 문자가 이와 같은 처리에 대한 인정 기관)의 ToUpper 대에 ToLower는에 관련 게시물이 있습니다

    "- 사용의 ToUpper보다는 ToLower는, 및 OS 케이스 규칙을 선택하기 위해 InvariantCulture를 지정 String.ToUpper는"그는 말한다

  2. ==============================

    2.내가 사용 System.Data.Linq.SqlClient.SqlMethods.Like (row.Name, "테스트") 내 쿼리한다.

    내가 사용 System.Data.Linq.SqlClient.SqlMethods.Like (row.Name, "테스트") 내 쿼리한다.

    그러면 대소 문자를 구분 비교를 행한다.

  3. ==============================

    3.나는이 사용하는 람다 식을 시도하고 일했다.

    나는이 사용하는 람다 식을 시도하고 일했다.

    목록 .ANY (X => (String.Equals (x.Name 이름, StringComparison.OrdinalIgnoreCase)) && (x.Type == qbType));

  4. ==============================

    4.당신은 LINQ는 - 투 - SQL이 변경되지 않은 SQL에 전달 얻을 것이다으로 대소 문자를 구분하는 문자열을 통과하면 비교가 데이터베이스에 발생합니다. 당신이 원하는 경우 데이터베이스의 대소 문자가 구분되지 않는 문자열 비교는 모든 당신은 비교 그대로 당신의 문자열을 SQL 쿼리로 그 표현을 번역 할 LINQ - 투 - SQL 제공을하는 람다 식을 만들 수있다 할 필요가있다.

    당신은 LINQ는 - 투 - SQL이 변경되지 않은 SQL에 전달 얻을 것이다으로 대소 문자를 구분하는 문자열을 통과하면 비교가 데이터베이스에 발생합니다. 당신이 원하는 경우 데이터베이스의 대소 문자가 구분되지 않는 문자열 비교는 모든 당신은 비교 그대로 당신의 문자열을 SQL 쿼리로 그 표현을 번역 할 LINQ - 투 - SQL 제공을하는 람다 식을 만들 수있다 할 필요가있다.

    예를 들어이 LINQ의 쿼리 :

    from user in Users
    where user.Email == "foo@bar.com"
    select user
    

    LINQ - 투 - SQL 공급자의 다음과 같은 SQL로 번역 가져옵니다

    SELECT [t0].[Email]
    FROM [User] AS [t0]
    WHERE [t0].[Email] = @p0
    -- note that "@p0" is defined as nvarchar(11)
    -- and is passed my value of "foo@bar.com"
    

    당신이 볼 수 있듯이, 문자열 매개 변수는 일들이 당신에게 기대하는 단지 방식으로 작동한다고 의미하는 SQL에 비교됩니다.

  5. ==============================

    5.SQL 쿼리 Linq에 민감한 경우 선언 수행하려면 '문자열'필드는 다음 중 하나를 사용하여 서버에 데이터 유형을 지정하여 대소하는 단계;

    SQL 쿼리 Linq에 민감한 경우 선언 수행하려면 '문자열'필드는 다음 중 하나를 사용하여 서버에 데이터 유형을 지정하여 대소하는 단계;

    varchar(4000) COLLATE SQL_Latin1_General_CP1_CS_AS 
    

    또는

    nvarchar(Max) COLLATE SQL_Latin1_General_CP1_CS_AS
    

    참고 : 위의 데이터 정렬 유형 수단 '대소 문자 구분'의 'CS'.

    비주얼 스튜디오 DBML 디자이너를 사용하여 속성을 볼 때이 작업은 "서버 데이터 형식"필드에 입력 할 수 있습니다.

    자세한 내용은 참조하십시오 http://yourdotnetdesignteam.blogspot.com/2010/06/case-sensitive-linq-to-sql-queries.html

  6. ==============================

    6.

    where row.name.StartsWith(q, true, System.Globalization.CultureInfo.CurrentCulture)
    
  7. ==============================

    7.다음 2 단계 접근법은 나를 위해 작동 (VS2010, ASP.NET MVC3, SQL 서버 2008 SQL에 LINQ를)

    다음 2 단계 접근법은 나를 위해 작동 (VS2010, ASP.NET MVC3, SQL 서버 2008 SQL에 LINQ를)

    result = entRepos.FindAllEntities()
        .Where(e => e.EntitySearchText.Contains(item));
    
    if (caseSensitive)
    {
        result = result
            .Where(e => e.EntitySearchText.IndexOf(item, System.StringComparison.CurrentCulture) >= 0);
    }
    
  8. ==============================

    8.이 작업을 실행하면 실패 할 수 있도록 때로는 데이터베이스에 저장된 값은 공백을 포함 할 수있다

    이 작업을 실행하면 실패 할 수 있도록 때로는 데이터베이스에 저장된 값은 공백을 포함 할 수있다

    String.Equals(row.Name, "test", StringComparison.OrdinalIgnoreCase)
    

    이 문제에 대한 해결 방법은 다음과 같이 선택 후 다음의 경우 변환 공간을 제거하는 것입니다

     return db.UsersTBs.Where(x => x.title.ToString().ToLower().Replace(" ",string.Empty).Equals(customname.ToLower())).FirstOrDefault();
    

    이 경우 참고

    customname는 데이터베이스 값과 일치하는 값이다

    UsersTBs는 클래스

    제목은 데이터베이스 열입니다

  9. ==============================

    9.이 효율적으로 작동하는 쿼리가 작동하는지 사이의 여부에 차이가 있음을 기억하십시오! 명령문의 대상이 SQL 서버 때 생산 될 것 T-SQL에 대해 생각해야합니다 그래서 LINQ 문은 T-SQL로 변환됩니다.

    이 효율적으로 작동하는 쿼리가 작동하는지 사이의 여부에 차이가 있음을 기억하십시오! 명령문의 대상이 SQL 서버 때 생산 될 것 T-SQL에 대해 생각해야합니다 그래서 LINQ 문은 T-SQL로 변환됩니다.

    사용 String.Equals 가장 가능성이 다시 모든 SQL Server에서 행 가져 (I 추측하고있다)하고 T-SQL로 변환 할 수없는 .NET 표현이기 때문에 다음 .NET에서 비교를 할 것입니다.

    데이터 액세스를 증가 및 색인을 활용하는 능력을 제거하는 식을 사용하여 즉. 그것은 작은 테이블에서 작동합니다 그리고 당신은 차이를 통지하지 않습니다. 큰 테이블에 매우 심하게 수행 할 수 있습니다.

    즉 LINQ에 존재하는 문제 중 하나입니다; 사람들은 더 이상 그들이 작성하는 문이 성취되는 방법에 대해 생각하지 않습니다.

    심지어 T-SQL에서 -이 경우 식을 사용하지 않고 당신이 원하는 것을 할 수있는 방법이 없다. 따라서 좀 더 효율적으로이 작업을 수행 할 수 없습니다. 심지어 T-SQL 응답 위에서 주어진 (정렬과 변수를 사용하여)는 인덱스에서 가장 가능성이 결과는 무시하지만, 그것은 큰 테이블이 다음의 경우 인덱스가 사용 된 경우 그것은 가치가 문을 실행하고 볼 수있는 실행 계획을보고있다 .

  10. from https://stackoverflow.com/questions/841226/case-insensitive-string-compare-in-linq-to-sql by cc-by-sa and MIT license