有趣的大小寫問題 utf8 bin

2021-09-23 23:02:34 字數 2934 閱讀 7087

問題:

***@3023 14:51:26>insert into test_tmp_log_node_10445__01 select * from test;

error 1062 (23000): duplicate entry 『taobao|維西v』 for key 『idx_nodetemp_10445_01』

檢視表結構:

create table `test` (

`user_id` varchar(64) character set utf8 collate utf8_bin not null comment 『主鍵。客戶全域性統一id,由客戶統一id生成規則生成』,

`control_group_type` int(2) not null default 『0』

) engine=innodb default charset=utf8;

create table `test_tmp_log_node_10445__01` (

`user_id` varchar(64) default null,

`control_group_type` tinyint(4) default null,

unique key `idx_nodetemp_10445_01` (`user_id`)

) engine=innodb default charset=utf8;

bakdb_jwswg888@3023 15:49:38>select count(user_id),count(*),count(distinct user_id) from test;

+—————-+———-+————————-+

| count(user_id) | count(*) | count(distinct user_id) |

+—————-+———-+————————-+

| 1700241 | 1700241 | 1700241 |

+—————-+———-+————————-+

可以看到對user_id做統計,user_id的資料是唯一,但是為什麼在插入到test_tmp_log_node_10445__01中報主鍵衝突喃?

我們來看看test表中類似『維西v』的資料:

bakdb_jwswg888@3023 15:31:28>select * from t1 where user_id like 『%維西%』;

+———————+——————–+

| user_id | control_group_type |

+———————+——————–+

| taobao|vici維西 | -1 |

| taobao|化雨維西 | -1 |

| taobao|維西v | -1 |

| taobao|維西v | -1 |

| taobao|胡維西 | -1 |

可以看到test表確實有兩條』taobao|維西v』的資料,所以插入到test_tmp_log_node_10445__01中報主鍵衝突了,那為什麼user_id distinct值和sum是相同的?對test表新增唯一索引驗證一下:

bakdb_jwswg888@3023 15:56:22>alter table test add unique key uk_userid(user_id);

query ok, 0 rows affected (20.38 sec)

records: 0 duplicates: 0 warnings: 0

可以看到test表示是可以在user_id上面新增唯一索引的,則證明在test中user_id的確是唯一的,但在插入到test_tmp_log_node_10445__01中就衝突,那裡出了問題?

這裡看到test中user_id欄位的字符集有些異常:character set utf8 collate utf8_bin,而test_tmp_log_node_10445__01中user_id欄位的字符集則沒有明顯指定,難道是這裡有問題?

bakdb_jwswg888@3023 15:29:48>create table t1 (user_id varchar(64),control_group_type int);

query ok, 0 rows affected (0.05 sec)

bakdb_jwswg888@3023 15:30:35>insert into t1 select * from test;

query ok, 1700241 rows affected (17.39 sec)

records: 1700241 duplicates: 0 warnings: 0

bakdb_jwswg888@3023 15:31:02>select count(user_id),count(*),count(distinct user_id) from t1;

+—————-+———-+————————-+

| count(user_id) | count(*) | count(distinct user_id) |

+—————-+———-+————————-+

| 1700241 | 1700241 | 1700240 |

+—————-+———-+————————-+

哇哦,可以看到新建立的t1表中user_id已經出現了重複資料了,在仔細發現:

| taobao|維西v | -1 |

| taobao|維西v | -1 |

可以看到乙個是「v」,乙個是小「v」,原來是大小寫的問題,在test表中指定了utf8_bin字符集 ,該字符集是區分大小寫的:

utf8_general_ci 不區分大小寫

utf8_general_cs 區分大小寫

utf8_bin: 將字串每個字串用二進位制資料編譯儲存, 區分大小寫,而且可以存二進位制的內容

所以在建立test_tmp_log_node_10445__01表的時候指定一下user_id列的屬性為:user_id varchar(64) binary則可以區分大小寫。

Mysql區分大小寫(大小寫敏感)的問題總結

mysql預設是不區分大小寫的,但是在很多情況下需要大小敏感,以下總結了多種設定mysql大小寫敏感的方法。方法一 修改mysql server安裝目錄下的 my.ini 檔案,在mysqld節下加入下面一行 set variable lower case table names 0 0 大小寫敏感...

mysql 的大小寫問題

在windows下,mysql預設是不區分大小寫的。想要設成區分大小寫,網上隨便一搜就能搜到,就是在my.inf裡加上這句話 lower case table names 0 lower case table names這個引數是什麼意思呢?看一下mysql文件 如果設定為1,表名用小寫儲存到硬碟上...

MySQL的大小寫問題

mysql在linux下資料庫 表名 列名 別名的規則 1.資料庫名與表名是嚴格區分大小寫 2.表的別名是嚴格區分大小寫的 3.變數名嚴格區分大小寫 4.列名與列的別名忽略大小寫。mysql在windows下不區分大小寫。原因 mysql在查詢字串時是大小寫不敏感的,在編譯mysql時一般以iso ...