Tôi không nghĩ rằng bạn có vấn đề với các mối quan hệ. Tôi nghĩ thay vào đó, vấn đề là bằng cách sử dụng các khóa thay thế (ví dụ Id) cho mỗi bảng, cơ sở dữ liệu kết quả không thể ngăn Công nhân được chèn vào Bộ phận của một Công ty trong khi Phân loại là của một Công ty khác và ngược lại. Một cách tốt để hiểu điều này là trực quan hóa lược đồ bằng công cụ Lập biểu đồ ER. Tôi sẽ sử dụng công cụ Oracle Data Modeler , một bản tải xuống miễn phí.
Sơ đồ ER

Khi nó đứng, bạn có thể có 2 công ty - nói IBMvà Microsoft. IBMcó thể có một Software Developmentbộ phận và Microsoft có thể có một Desktop Softwarebộ phận. IBM có thể có một Software Engineerphân loại và Microsoft có thể có một Software Developerphân loại. Bây giờ, vì bạn có một khóa thay thế cho Departmentvà Classification, thực tế đó Software Developmentlà một IBMbộ phận và Desktop Softwarelà một Microsoftbộ phận bị mất cho các mối quan hệ trẻ em trong tương lai. Đây cũng là trường hợp với Classification. Do đó, rất dễ để vô tình gán Harlan Mills, ai là IBMnhân viên trong Software Developmentbộ phận, phân loại trong Software Developerđó là mộtMicrosoftphân loại! Tương tự như vậy, công nhân có thể được phân loại đúng và sai bộ phận! Đây là một sơ đồ hiển thị ví dụ đầu tiên:

1 Id đại diện IBMvà 2 Id đại diện Microsoft. Tôi đã đánh dấu màu đỏ vào kịch bản trong đó Harlan Millsvà Bill Gatesđược gán cho các bộ phận sai, được hiển thị bằng Id bộ phận 10 được liên kết với 200 Id phân loại và ngược lại.
Tùy chọn để giải quyết
Vì vậy, các tùy chọn để ngăn chặn anh ta xảy ra là gì? Có hai lựa chọn ngay lập tức. Đầu tiên là nhận ra rằng bằng cách sử dụng khóa thay thế cho mỗi bảng, vấn đề này tồn tại và giới thiệu chương trình bổ sung để xác minh nó không xảy ra. Điều này có thể được thực hiện trong ứng dụng, nhưng nếu việc chèn và cập nhật có thể xảy ra bên ngoài ứng dụng thì các liên kết không chính xác vẫn có thể xảy ra. Một cách tiếp cận tốt hơn sẽ là tạo ra một trình kích hoạt kích hoạt tính năng chèn và cập nhật của nhân viên để đảm bảo rằng bộ phận được phân công thuộc cùng công ty với phân loại được chỉ định và nếu không thất bại trong việc chèn hoặc cập nhật.
Tùy chọn thứ hai là không sử dụng các khóa thay thế cho mỗi bảng. Thay vào đó, chỉ sử dụng các khóa thay thế cho Companybảng, đây là cơ bản và không có cha mẹ, sau đó tạo các mối quan hệ xác định cho các bảng con Departmentvà Classificationbảng con. Các bảng Departmentvà Classificationbây giờ có PK Company Idcộng với Số thứ tự hoặc Tên để phân biệt chúng. Sau đó, các mối quan hệ từ Departmentvà Classificationđể Workercũng trở thành identifyingvà do đó các PK của Workertrở thành Company Id, cộng với Department Number(Tôi đang sử dụng một số thứ tự trong ví dụ này), cộng với Classification Number. Kết quả là chỉ có one Company Idtrong Workerbảng. Bây giờ không thể chỉ định mộtWorkermột Departmenttrong một Companyvà một Classificationtrong một khác Company.
Tại sao điều này là không thể? Nó là không thể bởi vì các lược đồ thực hiện toàn vẹn tham chiếu giữa Workervà Departmentvà Classification. Nếu một nỗ lực được thực hiện để chèn một Workercho một Departmenttrong một Companyvà và Classificationcủa người khác, sự kết hợp đó không tồn tại trong bảng cha tương ứng sẽ kích hoạt một sự vi phạm toàn vẹn tham chiếu và chèn sẽ không làm việc.
Dưới đây là sơ đồ cập nhật về việc thực hiện tùy chọn thứ hai:

Tùy chọn ưa thích
Trong hai tùy chọn, tôi hoàn toàn thích cách thứ hai - sử dụng các mối quan hệ xác định và khóa xếp tầng - vì hai lý do. Đầu tiên, tùy chọn này đạt được quy tắc mong muốn mà không cần lập trình bổ sung. Phát triển một kích hoạt là không tầm thường. Nó phải được mã hóa, thử nghiệm và duy trì. Đảm bảo logic kích hoạt là tối ưu để không ảnh hưởng đến hiệu suất cũng không phải là nhỏ. Cuốn sách Toán học ứng dụng cho các chuyên gia cơ sở dữ liệu cung cấp rất nhiều chi tiết về sự phức tạp của một giải pháp như vậy. Thứ hai, các quy tắc ngụ ý rằng Bộ và Phân loại không thể tồn tại bên ngoài bối cảnh của Company, và vì vậy lược đồ bây giờ phản ánh chính xác hơn thế giới thực.
Đây là một câu hỏi tuyệt vời bởi vì nó cho thấy chính xác lý do tại sao chỉ cần giả sử mỗi bảng yêu cầu khóa thay thế là một ý tưởng tồi. Fabian Pascal có một bài đăng blog tuyệt vời về chủ đề này cho thấy rằng khóa không chỉ có thể là một ý tưởng tồi từ quan điểm toàn vẹn dữ liệu mà còn có thể khiến một số truy xuất chậm hơnở cấp độ vật lý chính xác bởi vì các phép nối được yêu cầu rằng, có các khóa được xếp tầng chính xác, sẽ không cần thiết. Một chủ đề thú vị khác mà câu hỏi này tiết lộ là một cơ sở dữ liệu không thể đảm bảo rằng tất cả dữ liệu được chèn vào đó là chính xác đối với thế giới thực. Thay vào đó, nó chỉ có thể đảm bảo rằng dữ liệu được chèn vào nó phù hợp với các quy tắc được khai báo. Trong trường hợp này, chúng ta có thể làm tốt nhất có thể bằng cách sử dụng cách tiếp cận khóa xếp tầng để đảm bảo DBMS có thể giữ dữ liệu phù hợp với quy tắc rằng một Workertrong những Companynhu cầu nhất định phải được chỉ định Classificationvà Departmenttương tự Company. Nhưng, nếu trong thế giới thực Microsoftcó một bộ phận được gọi Desktop Softwarenhưng người dùng cơ sở dữ liệu sẽ xác nhận bộ phận đó làSoftware Development DBMS không thể làm gì khác ngoài việc cho rằng nó đã được đưa ra một sự thật.