關(guān)于查找沒有主鍵的表這件事,我在網(wǎng)上看了一大堆灼卢,基本都是互相抄,全都一個樣来农,而且那SQL寫的也不好鞋真,我想查個沒有主鍵的表,還得手動替換庫名沃于,那我要是有20個庫我得查20次涩咖?更何況排除系統(tǒng)表的方式也很奇怪……所以我就自己寫了一個,能查所有庫的所有表繁莹,舒服了檩互。
壓縮版
SELECT a.TABLE_SCHEMA,a.TABLE_NAME FROM (SELECT TABLE_SCHEMA,TABLE_NAME FROM information_schema.TABLES WHERE TABLE_SCHEMA NOT IN('mysql','information_schema','performance_schema','sys','sysdb')) as a LEFT JOIN (SELECT TABLE_SCHEMA,TABLE_NAME FROM information_schema.TABLE_CONSTRAINTS WHERE CONSTRAINT_TYPE='PRIMARY KEY' AND TABLE_SCHEMA NOT IN('mysql','information_schema','performance_schema','sys','sysdb')) as b ON a.TABLE_SCHEMA=b.TABLE_SCHEMA AND a.TABLE_NAME=b.TABLE_NAME WHERE b.TABLE_NAME IS NULL;
美化版
SELECT
a.TABLE_SCHEMA,
a.TABLE_NAME
FROM
(
SELECT
TABLE_SCHEMA,
TABLE_NAME
FROM
information_schema.TABLES
WHERE
TABLE_SCHEMA NOT IN ( 'mysql', 'information_schema', 'performance_schema', 'sys', 'sysdb' )) AS a
LEFT JOIN (
SELECT
TABLE_SCHEMA,
TABLE_NAME
FROM
information_schema.TABLE_CONSTRAINTS
WHERE
CONSTRAINT_TYPE = 'PRIMARY KEY'
AND TABLE_SCHEMA NOT IN ( 'mysql', 'information_schema', 'performance_schema', 'sys', 'sysdb' )) AS b
ON a.TABLE_SCHEMA = b.TABLE_SCHEMA
AND a.TABLE_NAME = b.TABLE_NAME
WHERE
b.TABLE_NAME IS NULL;
sql解釋
查詢結(jié)果中TABLE_SCHEMA是庫名,TABLE_NAME就是表名咨演。
其查詢原理就是information_schema庫中存儲了各個庫與表的結(jié)構(gòu)闸昨,在information_schema.TABLES
表中存儲了所有表,information_schema.TABLE_CONSTRAINTS
表中存儲了表相關(guān)的約束,主鍵就是一種約束饵较,所以CONSTRAINT_TYPE字段為PRIMARY KEY值的就是擁有主鍵的表拍嵌。
有了所有表的表名,還有了所有擁有主鍵的表循诉,那么就簡單了横辆,以查詢出的全部表為主表,左聯(lián)一下茄猫,右表為空的就是沒有主鍵的表狈蚤。
SQL中排除了mysql自帶的五個庫,同時解決了不同名的庫擁有相同名的表的情況划纽,還有優(yōu)化空間脆侮,不過我覺得不是業(yè)務(wù)SQL,沒必要優(yōu)化了阿浓。