【发布时间】:2014-05-10 21:25:21
【问题描述】:
考虑这个例子:
数据库(类似于 Stackoverflow)有一个表,同一个表中的问题和答案可通过PostType 字段区分。我想取回最新帖子的列表,无论是问题还是答案。
由于问题和答案具有共同的属性,因此两个类都继承自抽象类 ContentBase。他们只添加了一些与每种类型相关的额外字段。
如何根据条件字段获取转换为 IList<ContentBase> 的内容项目列表,而单个项目属于具体类型 Question 或 Answer。
public abstract class ContentBase
{
public int Id { get; set; }
public string Title { get; set; }
public User Author { get; set; }
public abstract ContentType Type { get; }
...
}
public class Question : ContentBase
{
public override ContentType Type
{
get { return ContentType.Question; }
}
...
}
public class Answer: ContentBase
{
public override ContentType Type
{
get { return ContentType.Answer; }
}
...
}
然后我的存储库会有一个调用:
IList<ContentBase> result = db.GetLatest();
我正在使用 PetaPoco/NPoco,但我想如果使用 Dapper 也会出现同样的问题。
问题
如何指示 DAL 根据特定字段的值(在本例中为 ContentType)实例化正确的具体类型?
说明
我应该这样做:
db.Fetch<ContentBase, User>(...)
但我不能,因为ContentBase 是一个抽象类。如果我将此行更改为:
db.Fetch<dynamic, User>(...)
它仍然不起作用,因为我从 NPoco 收到了一个 InvalidOperationException,说 无法自动加入用户。
我想这样做的唯一方法是创建一个继承自PocoData 的新类并提供我自己的GetFactory 委托实现。 我认为。我认为没有任何其他可扩展点可以实例化具体的 POCO,我不确定我是否应该这样做以及如何,因为我' m 处理抽象祖先类。
【问题讨论】:
-
如果你使用
var result = db.Fetch<Question>("Select * from ContentBase ..",你会得到问题...但是如果你想要一个包含问题和答案的列表,那么将它们分开不是 DAL 的工作。 -
@EduardoMolteni:没错。 DAL 不应该知道不同的内容类型,因此应该只返回适当的实例。您的意思是我应该进行 N 个 DB 调用,每种类型调用一个并将它们组合起来?
-
不不不。使用 LINQ 等进行 1 个 DB 调用并分离或转换
-
@EduardoMolteni:这正是我想要做的。我同时从数据库中得到问题和答案,但我的结果应该包括正确的类型(它们都继承自
ContentBase)。我只是不知道该怎么做?我该怎么做?你能用一些代码写一个答案,以便更清楚你想告诉我什么吗?让我更新一下我的问题... -
对不起,我错过了
abstract部分,现在我明白你的意思了。
标签: c# petapoco mapper table-per-hierarchy npoco