Giới thiệu
Trong hướng dẫn này, tôi sẽ giải thích khái niệm Mệnh đề HAVING và WHERE trong SQL Server. Bài viết chi tiết này sẽ bao gồm các chủ đề sau như sau,
- Giới thiệu
- Lệnh thực thi trong SQL
- Mệnh đề HAVING
- Mệnh đề WHERE
- Sự khác biệt giữa mệnh đề HAVING và WHERE
- Sự kết luận
Đầu tiên, hãy tạo một cơ sở dữ liệu với một số bảng chứa một số dữ liệu giả. Ở đây, tôi đang cung cấp cho bạn cơ sở dữ liệu cùng với các bảng chứa các bản ghi, trên đó tôi sẽ hiển thị cho bạn các ví dụ khác nhau. Hãy xem nào.
CREATE DATABASE OnkarSharma_OnlineFoodStore PRINT 'New Database ''OnkarSharma_OnlineFoodStore'' Created' GO USE [OnkarSharma_OnlineFoodStore] GO CREATE TABLE [dbo].[Employee] ( EmployeeID INT IDENTITY (31100,1), EmployerID BIGINT NOT NULL DEFAULT 228866, FirstName VARCHAR(50) NOT NULL, LastName VARCHAR(50) NOT NULL, Email VARCHAR(255) NOT NULL UNIQUE, DepartmentID VARCHAR(100) NOT NULL, Age INT NOT NULL, GrossSalary BIGINT NOT NULL, PerformanceBonus BIGINT, ContactNo VARCHAR(25), PRIMARY KEY (EmployeeID) ); CREATE TABLE [dbo].[tbl_Orders] ( OrderId INT IDENTITY (108, 1) PRIMARY KEY, FoodieID INT, OrderStatus TINYINT NOT NULL, -- OrderStatus: 4: Cancelled; 3: Pending; 2: Processing; 1: Completed OrderDate DATE NOT NULL, ShippedDate DATE, RestaurantId INT NOT NULL, ); CREATE TABLE [dbo].[tbl_OrderItems]( OrderId INT NOT NULL, ItemId INT, MenuId INT NOT NULL, Quantity INT NOT NULL, Price DECIMAL(6, 2) NOT NULL, Discount DECIMAL(5, 2) NOT NULL DEFAULT 0, PRIMARY KEY (ItemId) ); CREATE TABLE [dbo].[tbl_Menu] ( MenuId INT IDENTITY (81, 1) PRIMARY KEY, FoodCategoryID INT NOT NULL, FoodName VARCHAR (255) NOT NULL, TypeofFood VARCHAR (100) NOT NULL, Price DECIMAL(6, 2) NOT NULL );
Hãy kiểm tra các bảng sau của chúng tôi bằng cách sử dụng các truy vấn sau.
1) Để lấy dữ liệu từ bảng “Nhân viên”, hãy sử dụng truy vấn sau.
SELECT * FROM OnkarSharma_OnlineFoodStore..Employee
2) Để lấy dữ liệu từ bảng “tbl_Orders”, hãy sử dụng truy vấn sau.
SELECT * FROM OnkarSharma_OnlineFoodStore..tbl_Orders
3) Để lấy dữ liệu từ bảng “tbl_OrderItems”, hãy sử dụng truy vấn sau.
SELECT * FROM OnkarSharma_OnlineFoodStore..tbl_OrderItems
4) Để lấy dữ liệu từ bảng “tbl_Menu”, hãy sử dụng truy vấn sau.
SELECT * FROM OnkarSharma_OnlineFoodStore..tbl_Menu
Thứ tự thực thi trong SQL Server
Trước khi chuyển sang chủ đề chính, chúng ta cần biết thứ tự thực thi của truy vấn trong SQL Server. Thứ tự thực thi của SQL Server xác định thứ tự mà các mệnh đề của truy vấn được đánh giá.
FROM: Việc thực thi logic truy vấn SQL Server bắt đầu bằng câu lệnh “FROM”, câu lệnh này thu thập dữ liệu từ các bảng được đề cập trong truy vấn.
WHERE: Bước tiếp theo là mệnh đề “WHERE”, điều này lọc dữ liệu theo (các) điều kiện do người dùng xác định.
GROUP BY: Các “Mệnh đề GROUP BY ”thực hiện việc nhóm các bản ghi (dữ liệu) thu được từ (các) điều kiện WHERE.
HAVING: Đã đến lúc lọc các nhóm dựa trên các điều kiện cụ thể được tạo bởi mệnh đề “GROUP BY”. Và, điều này sẽ được thực hiện bởi mệnh đề HAVING.
SELECT: Bây giờ, quá trình xử lý đi xuống lệnh SELECT. Và, “SELECT” đánh giá cột nào sẽ được gửi trong kết quả. Nó cũng đánh giá bất kỳ từ khóa nào như UNIQUE, DISTINCT và TOP nếu nó được bao gồm.
ORDER BY: Cuối cùng, mệnh đề “ORDER BY” được sử dụng để sắp xếp dữ liệu theo tên cột được chỉ định trong đó. Theo mặc định, nó sắp xếp dữ liệu theo thứ tự tăng dần.
Mệnh đề HAVING
Mệnh đề HAVING được sử dụng cùng với mệnh đề GROUP BY để lọc dữ liệu từ các nhóm dựa trên các điều kiện được chỉ định trong mệnh đề HAVING. Mệnh đề HAVING chỉ áp dụng cho tổng thể các nhóm.
Key Points
- Mệnh đề HAVING chỉ có thể được sử dụng với Câu lệnh SELECT.
- Mệnh đề HAVING được sử dụng để lọc các bản ghi từ các nhóm. Điều này có nghĩa là nó được sử dụng để lọc các nhóm.
- Mệnh đề HAVING thực hiện trong các phép toán cột.
- Mệnh đề HAVING được sử dụng sau Mệnh đề GROUP BY.
- Mệnh đề HAVING có thể có các hàm tổng hợp.
- Mệnh đề HAVING chậm hơn mệnh đề WHERE và nên tránh sử dụng bất cứ khi nào có thể.
Syntax
CHỌN TỪ
WHERE
NHÓM THEO
CÓ <điều kiện>;
Các ví dụ
Các ví dụ trong phần này chứng minh chức năng của Mệnh đề HAVING. Hãy xem nào.
1) HAVING Clause with GROUP BY Clause
Ví dụ sau đây trả về danh sách các phòng ban có mức lương gộp trung bình lớn hơn 25L.
SELECT DepartmentID, AVG(GrossSalary) AS 'AvgGrossSalary' FROM OnkarSharma_OnlineFoodStore..Employee GROUP BY DepartmentID HAVING AVG(GrossSalary) > 2500000
2) HAVING Clause with WHERE Clause
Ví dụ sau trả về danh sách tổng số nhân viên cho các bộ phận tương ứng có Mức lương gộp cao hơn 23L.
SELECT COUNT(EmployeeID) AS TotalEmployees, DepartmentID, GrossSalary FROM OnkarSharma_OnlineFoodStore..Employee WHERE GrossSalary > 2300000 GROUP BY DepartmentID, GrossSalary HAVING COUNT(EmployeeID) < 7
3) HAVING Clause with ORDER BY Clause
Ví dụ sau trả về danh sách các phòng ban có Mức lương Tổng trung bình lớn hơn 25L theo thứ tự giảm dần.
SELECT DepartmentID, AVG(GrossSalary) AS 'AvgGrossSalary' FROM Employee GROUP BY DepartmentID HAVING AVG(GrossSalary) > 2500000 ORDER BY AvgGrossSalary DESC
4) HAVING Clause with Aggregate Functions
A) SUM()
Ví dụ sau đây tìm kiếm các đơn đặt hàng có tổng giá trị đơn hàng lớn hơn 1000.
SELECT OrderId, SUM((Quantity * Price) - Discount) AS 'TotalOrderValue' FROM OnkarSharma_OnlineFoodStore..tbl_OrderItems GROUP BY OrderId HAVING SUM((Quantity * Price) - Discount) > 1000 ORDER BY TotalOrderValue
B) MAX() & MIN()
Ví dụ sau đây tìm giá tối đa & tối thiểu cho từng loại danh mục thực phẩm.
SELECT FoodCategoryID, TypeofFood, MIN(Price) MinPrice, MAX(Price) MaxPrice FROM OnkarSharma_OnlineFoodStore..tbl_Menu GROUP BY FoodCategoryID, TypeofFood HAVING MIN(Price) > 20 OR MAX(Price) < 700
C) AVG()
Ví dụ sau đây tìm các danh mục thực phẩm với giá niêm yết trung bình từ 100 đến 500.
SELECT FoodCategoryID, TypeofFood, AVG(Price) 'AvgPrice' FROM OnkarSharma_OnlineFoodStore..tbl_Menu GROUP BY FoodCategoryID, TypeofFood HAVING AVG(Price) BETWEEN 100 AND 500
D) COUNT()
Ví dụ sau đây tìm người ăn (foodie) đã đặt ít hơn mười đơn hàng mỗi năm.
SELECT FoodieID, YEAR(OrderDate) AS [Order Year], DATENAME(MONTH ,(OrderDate)) Month, COUNT(OrderId) AS 'TotalOrders' FROM OnkarSharma_OnlineFoodStore..tbl_Orders GROUP BY FoodieID, YEAR (OrderDate), DATENAME(MONTH ,(OrderDate)) HAVING COUNT(OrderId) < 10
Mệnh đề WHERE
Mệnh đề WHERE được sử dụng để lọc các bản ghi của bảng. Nó thường được sử dụng với các lệnh DML (Ngôn ngữ thao tác dữ liệu), viz, CHỌN, CẬP NHẬT và XÓA. Mệnh đề WHERE áp dụng cho các hàng (bản ghi) riêng lẻ. Theo Wikipedia, “Mệnh đề WHERE chỉ định rằng câu lệnh Ngôn ngữ thao tác dữ liệu (DML) chỉ nên ảnh hưởng đến các hàng đáp ứng các tiêu chí đã chỉ định”.
Key Points
- Mệnh đề WHERE thường được sử dụng với các lệnh DML.
- Mệnh đề WHERE được sử dụng để lọc các hàng khỏi bảng.
- Mệnh đề WHERE thực hiện trong các hoạt động hàng.
- Mệnh đề WHERE đứng trước Mệnh đề GROUP BY.
- Mệnh đề WHERE không được chứa các điều kiện có hàm tổng hợp.
- Đây là một mệnh đề tùy chọn nhưng nó có thể được sử dụng để giới hạn số hàng bị ảnh hưởng bởi một câu lệnh DML.
- Mệnh đề WHERE nhanh hơn Mệnh đề HAVING.
Syntax
CHỌN TỪ
WHERE
Các ví dụ
Các ví dụ trong phần này chứng minh chức năng của Mệnh đề WHERE. Hãy xem nào.
1) SQL Server WHERE Clause
Ví dụ sau trả về danh sách nhân viên của bộ phận “V_IT” dưới 24 tuổi.
SELECT EmployeeID, CONCAT(FirstName , ' ' , LastName) AS [Full Name], Email, DepartmentID, GrossSalary FROM OnkarSharma_OnlineFoodStore..Employee WHERE Age < 24 AND DepartmentID = 'V_IT'
2) WHERE Clause with GROUP BY Clause
Ví dụ sau đây cung cấp tổng mức lương tổng cho các phòng ban “V_IT” và “V_HR”.
SELECT DepartmentID, SUM(GrossSalary) AS TotalGrossSalary FROM OnkarSharma_OnlineFoodStore..Employee WHERE DepartmentID IN ('V_IT', 'V_HR') GROUP BY DepartmentID
Những điểm cần nhớ
Theo Wikipedia, “WHERE được tính đến ở giai đoạn thực thi truy vấn trước đó, lọc các hàng được đọc từ các bảng. Nếu truy vấn chứa GROUP BY, các hàng từ bảng được nhóm lại và tổng hợp. Sau thao tác tổng hợp, HAVING được áp dụng, lọc ra các hàng không phù hợp với các điều kiện đã chỉ định. Do đó, WHERE áp dụng cho dữ liệu đọc từ bảng và HAVING chỉ nên áp dụng cho dữ liệu tổng hợp, chưa được biết trong giai đoạn đầu của truy vấn ”.
Không thể sử dụng mệnh đề HAVING mà không có câu lệnh SELECT hoặc với câu lệnh UPDATE và DELETE. Ngược lại, chúng ta có thể sử dụng Mệnh đề WHERE với các Câu lệnh CHỌN, CẬP NHẬT và XÓA (DML).
-- Wrong Queries SELECT * FROM Employee HAVING Salary > 3000000 UPDATE OnkarSharma_OnlineFoodStore..Employee SET DepartmentID = 'V_Admin' HAVING EmployeeID = 31100 DELETE FROM Employee HAVING EmployeeId > 31105
--Right Queries SELECT * FROM Employee WHERE Salary > 3000000 UPDATE OnkarSharma_OnlineFoodStore..Employee SET DepartmentID = 'V_Admin' WHERE EmployeeID = 31100 DELETE FROM Employee WHERE EmployeeId > 31105
Mệnh đề HAVING chậm hơn Mệnh đề WHERE và nên tránh khi có thể. Vì mệnh đề HAVING lọc dữ liệu sau khi thực hiện phép tính tổng hợp trong khi mệnh đề WHERE lọc các hàng trước khi thực hiện phép tính tổng hợp.
SELECT DepartmentID, AVG(GrossSalary) AvgGrossSalary FROM Employee GROUP BY DepartmentID HAVING DepartmentID IN ('V_Accounts', 'V_HR', 'V_MGR')
SELECT DepartmentID, AVG(GrossSalary) AvgGrossSalary FROM Employee WHERE DepartmentID IN ('V_Accounts', 'V_HR', 'V_MGR') GROUP BY DepartmentID
Một truy vấn (SELECT) có thể có cả mệnh đề WHERE và mệnh đề HAVING. Trong trường hợp đó, mệnh đề WHERE được áp dụng đầu tiên để lọc các hàng riêng lẻ trong bảng. Mệnh đề HAVING sau đó được áp dụng cho tập kết quả. Chỉ các nhóm thỏa mãn điều kiện HAVING mới xuất hiện trong đầu ra. Bạn có thể áp dụng mệnh đề HAVING cho chỉ những cột xuất hiện trong mệnh đề GROUP BY hoặc cũng có thể trong hàm tổng hợp.
SELECT DepartmentID, SUM(GrossSalary) AvgGrossSalary FROM Employee WHERE DepartmentID IN ('V_Accounts', 'V_HR', 'V_MGR') GROUP BY DepartmentID HAVING SUM(GrossSalary) > 5000000
Sự khác biệt giữa mệnh đề HAVING và WHERE trong SQL Server
Các mệnh đề HAVING và WHERE thường gây nhầm lẫn cho người mới bắt đầu cũng như người có kinh nghiệm, nhưng chúng phục vụ các mục đích khác nhau. Vì vậy, chúng ta hãy xem xét sự khác biệt nhanh chóng giữa mệnh đề HAVING và WHERE trong SQL Server.
S.No.
Key Points
HAVING Clause
WHERE Clause
1
Sự định nghĩa
Mệnh đề HAVING được sử dụng để lọc các bản ghi từ các nhóm.
Mệnh đề WHERE được sử dụng để lọc các hàng khỏi bảng.
2
Cú pháp
HAVING đứng sau Mệnh đề GROUP BY.
Mệnh đề WHERE đứng trước Mệnh đề GROUP BY.
3
Các điều kiện
Mệnh đề HAVING có thể có các hàm tổng hợp.
Nó không thể chứa các điều kiện với các hàm tổng hợp.
4
Loại hoạt động
Mệnh đề HAVING thực hiện trong các hoạt động cột cho các nhóm tóm tắt.
Mệnh đề WHERE thực hiện trong các hoạt động hàng.
5
Hoạt động như
Mệnh đề HAVING hoạt động như một bộ lọc sau.
Mệnh đề WHERE hoạt động như một bộ lọc trước.
6
Làm việc với
Mệnh đề HAVING chỉ có thể được sử dụng với câu lệnh SELECT.
Mệnh đề WHERE thường được sử dụng với các lệnh DML.
7
Tốc độ, vận tốc
Mệnh đề HAVING chậm hơn Mệnh đề WHERE.
Mệnh đề WHERE nhanh hơn Mệnh đề HAVING.
Hẹn gặp lại các bạn trong những bài viết tiếp theo, đến lúc đó hãy quan tâm và học tập vui vẻ nhé.
Bạn cũng có thể ghé thăm các bài viết khác của tôi,
- Sự khác biệt giữa các câu lệnh Xóa, Cắt ngắn và Bỏ trong SQL Server
- Các cách khác nhau để xử lý NULL trong SQL Server
Sự kết luận
Trong bài viết này, chúng ta đã thảo luận về khái niệm Mệnh đề HAVING và WHERE trong SQL Server với nhiều ví dụ khác nhau.
Tôi hy vọng bạn thích bài viết này. Hãy theo dõi C # Corner để biết thêm nhiều điều mới và thú vị về SQL Server.
Cảm ơn vì đã đọc.