2016-11-30 2 views
0

C'est une question de défi intéressant car il peut y avoir plusieurs façons de résoudre ce problème :)MySQL transformer champ unique sensible à la casse dans le champ de la casse unique,

J'ai une colonne ID est unique, mais sensible à la casse , ex:

----- ID ------ 
0018000001K6dkh -> record 1 
0018000001K6dkH -> record 2 (different from record 1) 

comme MySQL est sensible à la casse en UTF8, il envisage les deux valeurs d'ID comme identiques:

SELECT COUNT(*) FROM table WHERE id='0018000001K6dkh' //returns 2 instead of 1 
SELECT COUNT(*) FROM table WHERE id='0018000001K6dkH' //returns 2 instead of 1 

je dois construire une fonction MySQL que je peux ap nappe à cette colonne pour transformer tous les ID dans un insensible à la casse et uniques ID, ex:

function('0018000001K6dkh') = something 
function('0018000001K6dkH') = something different 
function('0018000000ttzlB') = something even different 
function('0018000000tTzlB') = something even more different 

Note: Je ne veux pas utiliser les collations, parce que je dois changer tout les WHERE s et JOIN s dans mon application (Laravel PHP). Je veux changer les ID de manière permanente.

+0

Je suis assez certain que vous pouvez changer le classement d'un champ. – Uueerdo

+0

lol tu as raison, ça marche. Voulez-vous répondre à la question? –

Répondre

1

C'est de MySQL http://dev.mysql.com/doc/refman/5.7/en/case-sensitivity.html

Pour provoquer une comparaison sensible à la casse des chaînes non binaires pour être insensible cas , l'utilisation COLLATE pour nommer un classement insensible à la casse. Les chaînes dans l'exemple suivant sont normalement sensibles à la casse, mais COLLATE change la comparaison insensible à la casse:

SET @s1 = 'MySQL' COLLATE latin1_bin; 
SET @s2 = 'mysql' COLLATE latin1_bin; 
SELECT @s1 = @s2; 

return false

utilisant @ s1 = @ COLLATE latin1_swedish_ci s2;

SELECT @s1 COLLATE latin1_swedish_ci = @s2; 

return true

ou utiliser BINARY

SELECT COUNT(*) FROM table WHERE BINARY id='0018000001K6dkh' 
SELECT COUNT(*) FROM table WHERE BINARY id='0018000001K6dkH' 
+0

J'ai changé le classement du champ de 'utf8_unicode_ci' à' utf8_bin' et tous les WHEREs et JOINs se comportent comme prévu (sensible à la casse) –

+0

@BassemLhm excellent .. bien – scaisEdge

2

Selon le MySQL documentation officiel, vous pouvez définir le classement sur une base par colonne (* voir data_type section pour CHAR, VARCHAR, TEXTE, ENUM et SET types). Cela devrait changer la manière par défaut dans laquelle ils sont comparés aux chaînes littérales et les uns aux autres, mais je ne suis pas familier avec les règles utilisées lors de la comparaison des champs de classement différents les uns avec les autres.

+0

J'ai changé le classement du champ de 'utf8_unicode_ci' à 'utf8_bin' et tous les WHEREs et JOINs se comportent comme prévu (sensible à la casse) –