sql >> Databasteknik >  >> RDS >> Sqlserver

SQL Server Like Query är inte skiftlägeskänslig

Problem:

Orsak:Kolumnen "Namn" har en skiftlägesokänslig (CI ) sammanställning.

Lösning:Du måste använda en CS sortering:SELECT * FROM fn_helpcollations() WHERE description LIKE N'%case-sensitive%' .

Obs! Det finns en databassortering och kolumnnivåsortering. Och det finns också en sortering på servernivå.

SELECT  DATABASEPROPERTYEX(DB_NAME(), 'Collation') AS DatabaseCollation
/*
-- Sample output (my database)
DatabaseCollation
----------------------------
SQL_Latin1_General_CP1_CI_AS
*/

SELECT  col.collation_name AS ColumnCollation
FROM    sys.columns col
WHERE   col.object_id = OBJECT_ID(N'dbo.Table_2') 
AND     col.name = N'Name'
/*
-- Sample output (my database)
ColumnCollation
----------------------------
SQL_Latin1_General_CP1_CI_AS
*/

Att bara ändra databassorteringen kommer INTE ändra sorteringen för befintliga användartabeller och kolumner:

Källa

Efter att ändrat databassortering , kommer utdata från ovanstående frågor att vara:

/*
DatabaseCollation -- changed
----------------------------
SQL_Latin1_General_CP1_CS_AS
*/

/*
ColumnCollation -- no change
----------------------------
SQL_Latin1_General_CP1_CI_AS
*/

och, som du kan se, sammanställningen av kolumnen Name förblir CI.

Ändra databassortering kommer dessutom endast att påverka de nyskapade tabellerna och kolumnerna. En ändring av databassorteringen kan alltså generera konstiga resultat (enligt min åsikt ) eftersom vissa [N][VAR]CHAR kolumner kommer att vara CI och de nya kolumnerna kommer att vara CS.

Detaljerad lösning #1:om bara några frågor för kolumnen Name måste vara CS sedan kommer jag att skriva om WHERE klausul i dessa frågor sålunda:

SELECT  Name 
FROM    dbo.Table_2
WHERE   Name LIKE 'Joe' AND Name LIKE 'Joe' COLLATE SQL_Latin1_General_CP1_CS_AS

Detta kommer att ge en ändring till SQL Server för att göra en Index Seek i kolumnen Name (i det finns ett index på kolumnen Name ). Dessutom kommer exekveringsplanen att inkludera en implicit konvertering (se Predicate egenskap för Index Seek ) på grund av följande predikat Name = N'Joe' COLLATE SQL_Latin1_General_CP1_CS_AS .

Detaljerad lösning #2:om alla frågor för kolumnen Name måste vara CS så ändrar jag sorteringen endast för kolumnen Name alltså:

-- Drop all objects that depends on this column (ex. indexes, constraints, defaults)
DROP INDEX IX_Table_2_Name ON dbo.Table_2

-- Change column's collation
ALTER TABLE dbo.Table_2
ALTER COLUMN Name VARCHAR(50) COLLATE SQL_Latin1_General_CP1_CS_AS
-- Replace VARCHAR(50) with proper data type and max. length
-- Replace COLLATE SQL_Latin1_General_CP1_CS_AS with the right CS collation

-- Recreate all objects that depends on column Name (ex. indexes, constraints, defaults)
CREATE INDEX IX_Table_2_Name ON dbo.Table_2 (Name)

-- Test query
SELECT  Name 
FROM    dbo.Table_2
WHERE   Name LIKE 'Joe'



  1. Visa fil lagrad i databasen med php i webbläsaren

  2. Xampp MySQL startar inte - "MYSQL startar inte på XAMPP 3.2.1 version..."

  3. Infoga PictureBox Image i SQL Server-databasen

  4. Konvertera kolumnsortering till standard för tabell/databas