c# Dapper、SplitOn:多个相同的参数问题 Multi-mapping one-to-many
c# Dapper, SplitOn: multiple same parameter issue Multi-mapping one-to-many
我有一个问题是 parent object 而不是 child object 上的 Dapper 查询拆分。结果每 child 返回一个 parent 行,给出许多重复的 parent,其中只有 1 个 child。
我探索的一个可能的问题是,如果 table1 和 table2 的主键在拆分函数中引起一些混淆,因为它们具有相同的名称 (.Id)。
问题是,我如何拆分 parent-child 行,以便在 SplitOn: 中使用相同的参数将许多 children 绑定到一个 parent 模型?
============================================= ============================
结论
在评论中我们得出结论,字典需要在函数之外,不需要多个 SplitOn:,一个就够了。
最后,字典确实提供了 Table1 的不同集合,每个集合代表 children。
查看评论了解更多详情。
============================================= =============================
var sql = $@"
SELECT * FROM Table1 t
INNER JOIN Table2 c ON c.Table1_Id = t.Id;";
var result = connection.Query<Table1, Table2, Table1>(
sql,
(table1, table2) =>
{
Table1 table1Entry;
Dictionary<int?, Table1> table1Dictionary = new Dictionary<int?, Table1>();
if (!table1Dictionary.TryGetValue(table1.Id, out tableEntry))
{
table1Entry = table1;
table1Entry.table2s = new List<Table2>();
tableDictionary.Add(table1Entry.Id, table1Entry);
}
tableEntry.table2s.Add(table2);
return table1Entry;
},
new
{
},
splitOn: "Id,Id");
将 Dictionary
与一对多 Dapper 查询一起使用的全部意义在于,您可以跟踪之前的 parents。为此,它必须在 Query
调用之外定义。你所拥有的每次都会在尝试查找之前创建一个新字典,所以它总是空的。
此外,如果两个表的第一列都是 "Id",那么您不需要在 splitOn
.
中指定它两次
Dictionary<int?, Table1> table1Dictionary = new Dictionary<int?, Table1>();
var result = connection.Query<Table1, Table2, Table1>(
sql,
(table1, table2) =>
{
Table1 table1Entry;
if (!table1Dictionary.TryGetValue(table1.Id, out tableEntry))
{
table1Entry = table1;
table1Entry.table2s = new List<Table2>();
tableDictionary.Add(table1Entry.Id, table1Entry);
}
tableEntry.table2s.Add(table2);
return table1Entry;
},
new
{
},
splitOn: "Id");
我有一个问题是 parent object 而不是 child object 上的 Dapper 查询拆分。结果每 child 返回一个 parent 行,给出许多重复的 parent,其中只有 1 个 child。
我探索的一个可能的问题是,如果 table1 和 table2 的主键在拆分函数中引起一些混淆,因为它们具有相同的名称 (.Id)。
问题是,我如何拆分 parent-child 行,以便在 SplitOn: 中使用相同的参数将许多 children 绑定到一个 parent 模型?
============================================= ============================
结论
在评论中我们得出结论,字典需要在函数之外,不需要多个 SplitOn:,一个就够了。
最后,字典确实提供了 Table1 的不同集合,每个集合代表 children。
查看评论了解更多详情。
============================================= =============================
var sql = $@"
SELECT * FROM Table1 t
INNER JOIN Table2 c ON c.Table1_Id = t.Id;";
var result = connection.Query<Table1, Table2, Table1>(
sql,
(table1, table2) =>
{
Table1 table1Entry;
Dictionary<int?, Table1> table1Dictionary = new Dictionary<int?, Table1>();
if (!table1Dictionary.TryGetValue(table1.Id, out tableEntry))
{
table1Entry = table1;
table1Entry.table2s = new List<Table2>();
tableDictionary.Add(table1Entry.Id, table1Entry);
}
tableEntry.table2s.Add(table2);
return table1Entry;
},
new
{
},
splitOn: "Id,Id");
将 Dictionary
与一对多 Dapper 查询一起使用的全部意义在于,您可以跟踪之前的 parents。为此,它必须在 Query
调用之外定义。你所拥有的每次都会在尝试查找之前创建一个新字典,所以它总是空的。
此外,如果两个表的第一列都是 "Id",那么您不需要在 splitOn
.
Dictionary<int?, Table1> table1Dictionary = new Dictionary<int?, Table1>();
var result = connection.Query<Table1, Table2, Table1>(
sql,
(table1, table2) =>
{
Table1 table1Entry;
if (!table1Dictionary.TryGetValue(table1.Id, out tableEntry))
{
table1Entry = table1;
table1Entry.table2s = new List<Table2>();
tableDictionary.Add(table1Entry.Id, table1Entry);
}
tableEntry.table2s.Add(table2);
return table1Entry;
},
new
{
},
splitOn: "Id");