Common Table Expressions (CTE) เป็นมาตราฐาน ANSI SQL:1999 แต่ SQL Server รองรับในเวอร์ชัน 2005 เริ่มใช้ได้กับ SELECT, INSERT, UPDATE, และ DELETE และคำสั่ง MERGE ตั้งแต่เวอร์ชัน SQL Server 2008 โดยได้นำมาใช้เพื่อช่วยให้การเขียน Query ที่ซับซ้อนอ่านง่ายขึ้นและรองรับการทำ Recursive Query (คิวรีแบบเรียกซ้ำ) แทนคิวรีที่มีความซับซ้อน มีการ Join กันหลายชั้น หรือต้องคำนวณซ้อนกันไปมา
CTE คืออะไร?
CTE คือ ผลลัพธ์ชั่วคราว (Temporary Result Set) ที่ถูกนิยามขึ้นมาเพื่อให้เราสามารถอ้างอิงถึงได้ภายในประโยคคำสั่ง SELECT, INSERT, UPDATE หรือ DELETE ตัวเดียว โดยมองว่ามันคือการสร้าง “ตารางเสมือน” ขึ้นมาใช้ชั่วคราวในขณะที่ Query กำลังทำงาน
โครงสร้างพื้นฐานของ CTE
เราจะเริ่มต้นด้วยคำสำคัญ WITH ตามด้วยชื่อของ CTE และนิยาม SQL ภายในวงเล็บ
WITH CTE_Name AS (
-- SQL statement to define the CTE
SELECT column1, column2
FROM table_name
WHERE condition
)
-- Query using the CTE
SELECT *
FROM CTE_Name;
ทำไมต้องใช้ CTE? (จุดเด่นที่สำคัญ)
- Readability (อ่านง่าย): แทนที่จะเขียน Subquery ซ้อนกันใน
FROMหรือWHEREจนงง เราสามารถแยก logic ออกมาเป็นส่วนๆ ด้านบนได้ - Reusability (ใช้ซ้ำได้): ภายใน Query เดียวกัน คุณสามารถเรียกใช้ CTE เดิมซ้ำได้หลายครั้ง (เช่น นำ CTE มา Self-join กันเอง)
- Recursion (การเรียกตัวเอง): นี่คือไม้ตายของ CTE ที่ Subquery ธรรมดาทำไม่ได้ คือการเขียน Recursive CTE เพื่อจัดการกับข้อมูลที่มีโครงสร้างเป็นลำดับชั้น (Hierarchy) เช่น ผังองค์กร หรือโครงสร้างสินค้า
ประเภทของ CTE
- Non-Recursive CTE
คือการใช้งานทั่วไปเพื่อจัดกลุ่มข้อมูลให้เป็นระเบียบ เช่น การหาค่าเฉลี่ยก่อนแล้วค่อยนำไป FilterWITH AverageSalary AS ( SELECT DepartmentID, AVG(Salary) as AvgSal FROM Employees GROUP BY DepartmentID ) SELECT e.Name, e.Salary, a.AvgSal FROM Employees e JOIN AverageSalary a ON e.DepartmentID = a.DepartmentID WHERE e.Salary > a.AvgSal; - Recursive CTE
ใช้สำหรับข้อมูลที่มีความสัมพันธ์เป็นทอดๆ เช่น การหาว่าพนักงานคนนี้อยู่ภายใต้สายการบังคับบัญชาของใครบ้าง โดยจะประกอบด้วยสองส่วนคือ Anchor member (จุดเริ่มต้น) และ Recursive member (ส่วนที่วนลูป) เชื่อมกันด้วยUNION ALLคุณสมบัติ CTE Subquery Temp Table (#) ความอ่านง่าย สูงมาก ต่ำ (ถ้าซ้อนเยอะ) ปานกลาง ขอบเขตการใช้งาน เฉพาะใน Query นั้น เฉพาะในวงเล็บนั้น ตลอดทั้ง Session การใช้ซ้ำ ได้ (ใน Query เดียวกัน) ไม่ได้ ได้ (จนกว่าจะลบ) Recursion รองรับ ไม่รองรับ ไม่รองรับ
สรุป
CTE เปรียบเสมือนการสร้างตัวแปรในโลกของ SQL ที่ช่วยให้เราจัดระเบียบความคิดและ Code ให้สะอาดขึ้น หากคุณต้องการเขียน Query ที่ซับซ้อนแต่ยังอยากให้เพื่อนร่วมงาน (หรือตัวคุณเองในอนาคต) อ่านรู้เรื่อง CTE คือทักษะที่คุณไม่ควรพลาดครับ
อ่านเพิ่มเติม