Cả hai đều mô tả mối quan hệ "has-a" (có một) giữa các đối tượng, nhưng khác nhau về mức độ sở hữu (ownership) và vòng đời (lifecycle).
Association (Liên kết)
Mối quan hệ "has-a" yếu (weak). Đối tượng A sử dụng đối tượng B, nhưng B có thể tồn tại độc lập, có thể được chia sẻ bởi nhiều A.
class Employee {
String name;
Address communicationAddress; // Association: Employee "có" Address
}
class Address {
String street, city, zipcode;
}
Addresscó thể tồn tại riêng, không phụ thuộcEmployee.- Một
Addresscó thể được tham chiếu bởi nhiềuEmployee. - Khi
Employeebị hủy,Addresscó thể vẫn sống.
Aggregation (Tổng hợp / Tập hợp)
Mối quan hệ "has-a" mạnh hơn (stronger), còn gọi là "whole-part" (toàn thể - phần). Đối tượng A chứa tập hợp các đối tượng B. B là "phần" của A, nhưng B vẫn có thể tồn tại độc lập khi A bị hủy.
class Department {
String name;
List employees; // Aggregation: Department "chứa" nhiều Employee
}
class Employee {
String name;
}
Departmentquản lý tập hợpEmployee.Employeecó thể chuyển department, hoặc tồn tại khi department giải thể.- Vẫn là "has-a" nhưng mang ý nghĩa tổ chức, quản lý tập hợp.
Bảng so sánh
| STT | Tiêu chí | Association | Aggregation |
|---|---|---|---|
| 1 | Định nghĩa | Quan hệ "has-a" giữa 2 class sử dụng lẫn nhau. | Quan hệ "has-a" + "whole-part": một class chứa tập hợp object class kia. |
| 2 | Sở hữu (Ownership) | Yếu - không sở hữu vòng đời. | Trung bình - quản lý tập hợp, nhưng phần tử độc lập. |
| 3 | Vòng đời (Lifecycle) | Độc lập hoàn toàn. | Phần tử có thể sống sau khi toàn thể chết. |
| 4 | Ràng buộc (Coupling) | Lỏng (loose coupling). | Chặt hơn (whole biết part, part có thể không biết whole). |
| 5 | Ký hiệu UML | Đường nét liền giữa 2 class. | Đường nét liền + hình thoi rỗng (hollow diamond) ở đầu whole. |
| 6 | Code Java | Field single reference: Address addr; |
Field collection: List<Employee> employees; |
| 7 | Ví dụ thực tế | Student - Course, Doctor - Patient, Car - Driver | Department - Employees, Library - Books, Team - Players |
Composition (Hợp thành) - Mức độ mạnh nhất
Để trọn vẹn, cần nhắc đến Composition - "part-of" thực sự, phần tử không thể tồn tại độc lập khi toàn thể chết.
class House {
// Room không tồn tại nếu House bị phá hủy
private List rooms = new ArrayList<>();
public House() {
rooms.add(new Room("Bedroom"));
rooms.add(new Room("Kitchen"));
}
}
class Room { String name; }
- UML: Hình thoi đặc (filled diamond) ở đầu whole.
- Java: Khởi tạo part trong constructor whole, không expose part ra ngoài, không cho phép set part từ ngoài.
Tóm tắt 3 mức độ "Has-A"
| Mức độ | Tên | Ownership | Lifecycle | UML | Ví dụ |
|---|---|---|---|---|---|
| Yếu | Association | Không | Độc lập | ── | Employee ↔ Address |
| Trung bình | Aggregation | Quản lý tập hợp | Part sống sót khi whole chết | ◇ (hollow diamond) | Department ↔ Employees |
| Mạnh | Composition | Sở hữu hoàn toàn | Part chết khi whole chết | ◆ (filled diamond) | House ↔ Rooms |
Lưu ý thực tế
- Trong code Java, Association và Aggregation thường trông giống nhau (field reference vs field collection). Khác biệt nằm ở ý nghĩa thiết kế (design intent).
- Composition thường implement bằng
private final List<Part>khởi tạo trong constructor, không có setter. - Đừng over-engineering: nhiều trường hợp chỉ cần Association đơn giản.