翻譯|行業資訊|編輯:董玉霞|2022-06-10 10:26:54.423|閱讀 260 次
概述:本文將介紹常見的SQL 查詢錯誤, 數據庫管理工具Navicat Premium是一套數據庫管理工具,讓你使用一個程序即可同時連接到 MySQL、MariaDB、SQL Server、SQLite、Oracle 和 PostgreSQL 數據庫。
# 界面/圖表報表/文檔/IDE等千款熱門軟控件火熱銷售中 >>
相關鏈接:
本文將介紹常見的SQL 查詢錯誤, 數據庫管理工具Navicat Premium是一套數據庫管理工具,讓你使用一個程序即可同時連接到 MySQL、MariaDB、SQL Server、SQLite、Oracle 和 PostgreSQL 數據庫。
在這個關于“常見的 SQL 查詢錯誤”的系列中,我們一直在探索看似直觀的 SQL 查詢構造方法如何導致反模式,從而導致錯誤結果和/或性能降低。上周,我們暫停了這個系列,討論了 SQL 中的謂詞。在本期文竟中,我們將學習它們的位置如何對查詢執行產生負面影響,尤其是在外部聯接中。
在鏈接相關的表和視圖時,可使用四種基本的聯接類型:內部聯接、左聯接、右聯接和外部聯接。內部聯接不會返回任何一個表中在另一個表中不匹配的行。外部聯接可以返回一個或兩個表中不匹配的行。而最后三種連接類型都是外部聯接的一種,其中:
雖然外部聯接在數據庫從業者中肯定占有一席之地,但即使在不需要它們的情況下,開發人員也傾向于使用它們。此外,外部聯接查詢可能會產生完全不同的結果,具體取決于你構建它的方式以及你在查詢中放置謂詞的位置。為了說明這一點,讓我們看看一個示例。
我們想檢索所有客戶的列表(無論他們是否下過任何訂單),以及自 2005 年 6 月開始以來他們下的訂單總數。為此,我們將使用外部聯接來鏈接 customers 和 orders 表,如下所示:
SELECT C.customerName, count(O.customerNumber) AS 2005_orders FROM customers AS C LEFT OUTER JOIN orders AS O ON C.customerNumber = O.customerNumber WHERE O.orderDate >= '2005-05-01' GROUP BY C.customerName ORDER BY 2005_orders DESC;
查詢結果應包含第一個表和第二個表中所有可能的行組合,也稱為笛卡爾積。不幸的是,當我們在 Navicat Premium 16 中運行查詢時,僅返回 13 行,盡管表中有 122 個客戶(未顯示):
為了理解哪里出了問題,讓我們一步一步從列和外部聯接開始重建查詢:
現在我們得到了所有的客戶。那些沒有下任何訂單的客戶的 customerNumbers 為 NULL,因為它們來自 orders 表。
現在,讓我們應用 WHERE 子句謂詞:
問題是 WHERE 子句中的謂詞將外部聯接變成了內部聯接。為了糾正這個問題,我們需要將 WHERE 謂詞添加到聯接條件:
我們現在可以調整原本的查詢以獲取所有客戶:
謹記要時刻注意篩選掉的行的位置。在上述示例中,WHERE 子句是問題所在。在一個更復雜的示例中,如果有多個聯接,錯誤的篩選可能發生在后續表運算符(如聯接到另一個表)而不是 WHERE 子句中。
更多有關Navicat Premium使用教程可點擊查看,歡迎加入Navicat Premium技術交流QQ群:765665608。
Navicat Premium 是一套數據庫管理工具,讓你使用一個程序即可同時連接到 MySQL、MariaDB、SQL Server、SQLite、Oracle 和 PostgreSQL 數據庫。了解更多購買詳情可聯系慧都在線客服。
本站文章除注明轉載外,均為本站原創或翻譯。歡迎任何形式的轉載,但請務必注明出處、不得修改原文相關鏈接,如果存在內容上的異議請郵件反饋至chenjj@fc6vip.cn