Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> C#

วิธีทำ Left Outer Join ด้วย LINQ Extension Methods ใน C#

ใน LINQ มีการจอยน์ (Join) หลายแบบ ซึ่งแตกต่างกันในการจัดการข้อมูลที่ไม่ตรงกัน (Non-matching elements):

  • INNER JOIN: นำเฉพาะข้อมูลที่ตรงกัน (Matching elements) เข้ามาในผลลัพธ์
  • LEFT OUTER JOIN: นำข้อมูลที่ตรงกันทั้งหมด รวมถึงข้อมูลที่ไม่ตรงจากฝั่งซ้าย (Left collection) เข้ามาในผลลัพธ์

ตัวอย่าง: สมมติมีคลาส Department และ Employee พนักงานชื่อ Mary ไม่มีแผนก (DepartmentID เป็น null) INNER JOIN จะไม่แสดง Mary แต่ LEFT OUTER JOIN จะแสดงพร้อมค่า "No Department"

ตัวอย่างโค้ด

static class Program
{
    static void Main(string[] args)
    {
        var result = Employee.GetAllEmployees()
            .GroupJoin(Department.GetAllDepartments(),
                e => e.DepartmentID,
                d => d.ID,
                (emp, depts) => new { emp, depts })
            .SelectMany(z => z.depts.DefaultIfEmpty(),
                (a, b) => new
                {
                    EmployeeName = a.emp.Name,
                    DepartmentName = b == null ? "No Department" : b.Name
                });

        foreach (var v in result)
        {
            Console.WriteLine(" " + v.EmployeeName + "\t" + v.DepartmentName);
        }
    }
}

public class Department
{
    public int ID { get; set; }
    public string Name { get; set; }
    public static List<Department> GetAllDepartments()
    {
        return new List<Department>()
        {
            new Department { ID = 1, Name = "IT" },
            new Department { ID = 2, Name = "HR" }
        };
    }
}

public class Employee
{
    public int ID { get; set; }
    public string Name { get; set; }
    public int? DepartmentID { get; set; } // ใช้ nullable เพื่อรองรับไม่มีแผนก
    public static List<Employee> GetAllEmployees()
    {
        return new List<Employee>()
        {
            new Employee { ID = 1, Name = "Mark", DepartmentID = 1 },
            new Employee { ID = 2, Name = "Steve", DepartmentID = 2 },
            new Employee { ID = 3, Name = "Ben", DepartmentID = 1 },
            new Employee { ID = 4, Name = "Philip", DepartmentID = 1 },
            new Employee { ID = 5, Name = "Mary" } // ไม่มี DepartmentID
        };
    }
}

ผลลัพธ์

Mark    IT
Steve   HR
Ben     IT
Philip  IT
Mary    No Department

คำอธิบายสำคัญ

  • GroupJoin: จัดกลุ่มข้อมูลจากฝั่งขวา (Right) ตามคีย์
  • DefaultIfEmpty(): หากไม่มีข้อมูลตรงกัน จะคืนค่า default (null สำหรับ reference type)
  • SelectMany: รวมผลลัพธ์จากกลุ่มข้อมูลเข้าด้วยกัน