यहां उपयोग किए गए समाधान का एक संस्करण है। मैंने इस मुद्दे को साइड-स्टेप किया, रोनी ने his answer में एक संपत्ति को शून्य करने के बजाय विरासत पदानुक्रम का उपयोग करके उठाया, लेकिन यह एक ही चीज़ के बराबर है।
यहां SQL है: उपयोगकर्ताओं के पास आइटम और संग्रह हैं, और आइटम संग्रह में हो सकते हैं।
CREATE TABLE Users
(id UNIQUEIDENTIFIER DEFAULT (NEWID()) NOT NULL,
name NVARCHAR (MAX) NULL,
email NVARCHAR (128) NULL,
PRIMARY KEY (id))
CREATE TABLE Items
(id UNIQUEIDENTIFIER DEFAULT (NEWID()) NOT NULL,
userId UNIQUEIDENTIFIER NOT NULL,
name NVARCHAR (MAX) NULL,
description NVARCHAR (MAX) NULL,
PRIMARY KEY (id),
FOREIGN KEY (userId) REFERENCES Users (id))
CREATE TABLE Collections
(id UNIQUEIDENTIFIER DEFAULT (NEWID()) NOT NULL,
userId UNIQUEIDENTIFIER NOT NULL,
name NVARCHAR (MAX) NULL,
layoutSettings NVARCHAR (MAX) NULL,
PRIMARY KEY (id),
FOREIGN KEY (userId) REFERENCES Users (id))
CREATE TABLE CollectedItems
(itemId UNIQUEIDENTIFIER NOT NULL,
collectionId UNIQUEIDENTIFIER NOT NULL,
PRIMARY KEY CLUSTERED (itemId, collectionId),
FOREIGN KEY (itemId) REFERENCES Items (id),
FOREIGN KEY (collectionId) REFERENCES Collections (id))
अब डेटा मॉडल कक्षाएं। एकाधिक प्रश्नों के साथ डैपर मल्टी मैपिंग से निपटने के लिए मैं अपेक्षा करता हूं कि संग्रह अपेक्षाकृत थोड़ा अधिक जटिल हो।
public class User
{
public Guid Id { get; set; }
public string Name { get; set; }
public string Email { get; set; }
public List<Item> Items { get; set; }
public List<Collection> Collections { get; set; }
}
public class Item
{
public Guid Id { get; set; }
public Guid UserId { get; set; }
public string Name { get; set; }
public string Description { get; set; }
}
public class CoreCollection
{
public Guid Id { get; set; }
public Guid UserId { get; set; }
public string Name { get; set; }
public string LayoutSettings { get; set; }
}
public class PartialDataCollection : CoreCollection
{
public Guid ItemId { get; set; }
}
public class Collection : CoreCollection
{
public List<Guid> ItemIds { get; set; }
}
public class CollectedItem
{
public Guid ItemId { get; set; }
public Guid CollectionId { get; set; }
public DateTime CreatedAt { get; set; }
}
अंत में हम नियंत्रक विधि है जो कई प्रश्नों
साथ साफ-सुथरी बहु मानचित्रण का उपयोग करता है
[Route("GetUser/{id}")]
public User GetUser(Guid id)
{
var sql = @"SELECT * FROM Users WHERE id = @id
SELECT * FROM Items WHERE userId = @id
SELECT * FROM Collections
LEFT OUTER JOIN CollectedItems ON Collections.id = CollectedItems.collectionId
WHERE userId = @id";
using (var connection = new SqlConnection(ConnectionString))
{
var multi = connection.QueryMultiple(sql, new { id = id });
var user = multi.Read<User>().Single();
var items = multi.Read<Item>().ToList();
var partialDataCollections = multi.Read<PartialDataCollection, CollectedItem, PartialDataCollection>(AddCollectedItem, splitOn: "itemId").ToList();
user.Items = items;
user.Collections = partialDataCollections.GroupBy(
pdc => pdc.Id,
(key, group) => new Collection
{
Id = key,
UserId = group.First().UserId,
Name = group.First().Name,
LayoutSettings = group.First().LayoutSettings,
ItemIds = group.Select(groupMember => groupMember.ItemId).ToList()
}).ToList();
return user;
}
}
private PartialDataCollection AddCollectedItem(PartialDataCollection collection, CollectedItem collectedItem)
{
if (collection != null && collectedItem != null)
{
collection.ItemId = collectedItem.ItemId;
}
return collection;
}
कहाँ रोनी his answer में person.Check = null
स्थापित करने के बारे में चिंतित है मैं जोड़ने से मेरा उत्तर में अतिरिक्त जटिलता के बारे में उत्सुक हूँ मेरे मॉडल में कक्षा PartialDataCollection
। लेकिन मैं इसके चारों ओर एक आसान तरीका नहीं देख सकता।
(नायब मैं इस an issue के रूप में साफ-सुथरी GitHub परियोजना पर उठाया है।)
+1, लेकिन यह लायक हो सकता है * * जवाब के रूप में यह स्वीकार नहीं कर आप देख रहे हैं यह करने के लिए एक बेहतर तरीका के लिए, चूंकि अनुत्तरित प्रश्न अधिक ध्यान आकर्षित करते हैं। – dumbledad
"चेकआईड" क्या है, आप इसे कहां से प्राप्त कर रहे हैं? – dumbledad
समझ गया - यह [splitOn:] (http://stackoverflow.com/a/7478958/575530) पैरामीटर – dumbledad