2010-06-17 30 views
5

Tôi có một appliaction quản lý danh sách lưu trữ dữ liệu của nó trong cơ sở dữ liệu quan hệ nhiều-nhiều.Làm thế nào để thể hiện mối quan hệ Nhiều-Nhiều trong XML hoặc định dạng tệp đơn giản khác?

I.E. Một ghi chú có thể nằm trong bất kỳ danh sách nào và danh sách có thể có bất kỳ số lượng ghi chú nào.

Tôi cũng có thể xuất dữ liệu này sang tệp XML và nhập tệp đó vào một phiên bản khác của ứng dụng của tôi để chia sẻ danh sách giữa những người dùng. Tuy nhiên, điều này được dựa trên một hệ thống di sản mà danh sách để lưu ý mối quan hệ là một-nhiều (lý tưởng cho XML).

Bây giờ, một ghi chú nằm trong nhiều danh sách được chia thành hai hàng giống nhau trong DB và tất cả các mối quan hệ giữa chúng sẽ bị mất.

Câu hỏi: Làm thế nào tôi có thể biểu diễn mối quan hệ nhiều-nhiều này theo định dạng tệp đơn giản, chuẩn? (Tốt hơn là XML để duy trì khả năng tương thích ngược)

Trả lời

6

Tôi nghĩ định dạng XML của bạn phải sử dụng một số loại "tham chiếu". Nếu bạn thích các mối quan hệ list-to-ghi chú để được hiển thị, sau đó một cái gì đó như sau có thể phù hợp:

<notes> 
    <note id="Note1"> ... </note> 
    <note id="Note2"> ... </note> 
    ... 
</notes> 

<lists> 
    <list id="List1"> 
     <note_refs> 
      <note_ref id="Note1"/> 
      <note_ref id="Note4"/> 
     </note_refs> 
    </list> 
    ... 
</lists> 

Nếu mặt khác bạn muốn xem một cách dễ dàng các danh sách liên kết với một lưu ý nhất định, sau đó bạn có thể đơn giản đảo ngược vai trò của danh sách và ghi chú trong ví dụ của tôi. Ngoài ra, bạn có thể biểu diễn mối quan hệ nhiều-nhiều hơn đối xứng toán học: xác định tất cả ghi chú, xác định tất cả các danh sách và sau đó xác định ánh xạ bao gồm [cặp tham chiếu danh sách, tham chiếu ghi chú].

+1

Đề xuất cuối cùng ở đây là cơ sở dữ liệu quan hệ sẽ làm như thế nào: bạn xác định hai bảng, "ghi chú" và "danh sách" và sau đó tham gia bảng "noteId", "listId" làm khóa chính (và chỉ có thể là dữ liệu). Vấn đề ở đây là hầu hết các giải pháp dựa trên XML sẽ làm cho những điều khó khăn hơn để truy vấn rằng một cơ sở dữ liệu quan hệ sẽ. Nếu tôi bị buộc phải sử dụng XML, tôi sẽ gắn bó với cách tiếp cận "note_ref" (giả sử rằng danh sách lái xe màn hình và ghi chú là thứ bạn có thể giữ trong bộ nhớ). Nếu không, tôi sẽ chuyển sang cơ sở dữ liệu và tham gia các bảng. XML là tuyệt vời cho một số thứ, nhưng không phải mọi thứ. – Godeke

+0

@Godeke Dữ liệu được lưu trữ trong cơ sở dữ liệu quan hệ. Đây chỉ là định dạng tệp đã xuất. – CodeFusionMobile

+0

@CSharperWithJava Trong trường hợp đó 99% nhận xét của tôi là mooted và tôi sẽ đơn giản đồng ý rằng phương pháp Note_Ref ở trên sẽ cho phép bạn đảm bảo rằng bạn không bị mất cấu trúc chi tiết của bản gốc (ghi chú thực tế là các thực thể đơn lẻ có liên quan đến). – Godeke

0

Cách duy nhất tôi có thể nghĩ để thực sự đại diện cho mối quan hệ nhiều-nhiều trong một XML hoặc bất kỳ cấu trúc phân cấp nào khác, là sử dụng nhiều mối quan hệ một-nhiều .

Dưới đây là một ví dụ đơn giản:

<list name="listA"> 
    <notes name="noteA" /> 
    <notes name="noteB" /> 
    <notes name="noteC" /> 
</list> 
<list name="listB"> 
    <notes name="noteB" /> 
    <notes name="noteC" /> 
    <notes name="noteD" /> 
</list> 

Nói cách khác, mỗi danh sách sẽ có ghi chú của mình như các nút con.

Nhiều nút con ghi chú sẽ được sao chép trong tệp XML. Quá trình điền vào cơ sở dữ liệu từ tệp XML sẽ phải ghi lại các nút con ghi chú trùng lặp.

Cách khác là chọn một danh sách cho từng ghi chú. Một ghi chú sẽ là nút con của chỉ một trong các danh sách. Ưu điểm là không có bất kỳ ghi chú trùng lặp nào. Điểm bất lợi là tệp XML không đại diện cho ghi chú để liệt kê các mối quan hệ đúng cách, có thể hoặc có thể không quan trọng.

+0

Đây là những gì tôi đã làm. Tôi có từng danh sách và sau đó mỗi ghi chú trong danh sách đó là một phần tử của danh sách đó. Vấn đề của tôi không phải là ghi chú trùng lặp, đó là mất thông tin khi tôi mất mối quan hệ nhiều-nhiều. – CodeFusionMobile

+0

@CSharperWithJava: Tôi không hiểu bạn đang mất thông tin gì. Mọi ghi chú con có thể có nhiều hơn một danh sách cha mẹ. Đó là ghi chú con sẽ được liệt kê như là một đứa trẻ của tất cả các danh sách mà nó có mối quan hệ với. –

+0

Tôi không thể giả định rằng hai yếu tố lưu ý giống nhau trên thực tế là cùng một lưu ý. Trong ví dụ của bạn, cả hai noteB có thể là cùng một lưu ý trong cả hai danh sách, trong khi noteC thực ra là hai ghi chú khác nhau. – CodeFusionMobile

0

bước đầu tiên của tôi sẽ là một cái gì đó đơn giản:

<notes> 
    <note> 
    <title>Groceries to get</title> 
    <list>shopping</list> 
    <list>urgent</list> 
    <body>eggs, cheese, milk</body> 
    </note> 
</notes> 

Would phù hợp với nhu cầu của bạn?

3

Trong cơ sở dữ liệu, công cụ để biểu diễn các mối quan hệ nhiều-nhiều là bảng kết hợp. Mỗi hàng trong bảng biểu diễn một liên kết giữa hai đối tượng.Vì vậy, nếu một lưu ý với một ID trong tổng số 1 xuất hiện trong danh sách với ID trong tổng số 1, 2, và 3, sẽ có ba hàng trong bảng hiệp hội:

ID NoteID ListID 
-- ------ ------ 
    1  1  1 
    2  1  2 
    3  1  3 

Bạn có thể nhận được một lưu ý và tất cả các danh sách liên quan của nó với một truy vấn như thế này:

SELECT [columns] FROM Association 
    JOIN Notes ON Note.ID = Association.NoteID 
    JOIN Lists ON List.ID = Association.ListID 
WHERE Association.NoteID = @NoteID 

Và tất cả các ghi chú cho một danh sách:

SELECT [columns] FROM Association 
    JOIN Notes ON Note.ID = Association.NoteID 
    JOIN Lists ON List.ID = Association.ListID 
WHERE Association.ListID = @ListID 

đó là cách bạn muốn thể hiện nó trong XML:

<Lists> 
    <List ID='1'>...</List> 
    <List ID='2'>...</List> 
    <List ID='3'>...</List> 
    ... 
<Lists> 
<Notes> 
    <Note ID='1'>...</Note> 
</Notes> 
<Associations> 
    <Association ID='1' NoteID='1' ListID='1'/> 
    <Association ID='2' NoteID='1' ListID='2'/> 
    <Association ID='3' NoteID='1' ListID='3'/> 
</Associations> 

Trong, XSLT, bạn có thể truy cập liên kết này như thế này:

<xsl:template match="List" mode="AssociatedNotes"> 
    <xsl:variable name="Associations" select="/*/Associations/Association[@ListID=current()/@ID]"/> 
    <xsl:apply-templates select="/*/Notes[@ID=$Associations/@NoteID]"/> 
</xsl:template> 

<xsl:template match="Note" mode="AssociatedLists"> 
    <xsl:variable name="Associations" select="/*/Associations/Association[@NoteID=current()/@ID]"/> 
    <xsl:apply-templates select="/*/Lists[@ID=$Associations/@ListID]"/> 
</xsl:template> 

(Lưu ý việc sử dụng các thuộc tính mode để giữ những mẫu này từ gọi nhau cho đến khi bạn có được một stack overflow).

0

Chỉ cần làm điều đó đơn giản như sau:

<notes> 
    <note id="1"> 
     <name>George</name> 
     <text>1984</text> 
     <notesLinks> 
      <listId id="1"/> 
     </notesLinks> 
    </note> 
    <note id="2"> 
     <name>George</name> 
     <text>animal farm</text> 
     <notesLinks></notesLinks> 
    </note> 
</notes> 
<lists> 
    <list id="1"> 
     <notesLinks> 
      <noteId id="1"/> 
      <noteId id="2"/> 
     </notesLinks> 
     <name>some info</name> 
    </list> 
</lists> 
Các vấn đề liên quan