1

我制作了两个都可以正常工作的查询,但我真的很难理解如何组合它们。我认为我最大的问题是我对查询使用了两种不同的语法,但我不确定如何在不使用“SQL-esque”标记的情况下表达我的第一个查询。

List<Task> tasksFromQueue = NHibernateSession.CreateQuery(
    "Select t from Task t, QueueLocation q where q.Queue.ID = :queueID and (t.SiteID = q.ComponentID or t.OriginalSiteID = q.ComponentID)")
    .SetParameter("queueID", queueID).List<Task>().ToList();

List<Task> tasksFromWorkflow = NHibernateSession
    .CreateCriteria(typeof(Task), "Task")
    .CreateCriteria("Task.Order", "Order")
    .CreateAlias("Task.TaskDevice", "TaskDevice").List<Task>();

IEnumerable<Task> tasks = tasksFromWorkflow.Intersect(tasksFromQueue);

如您所见,我有两个问题:

  • 对第一个查询使用详细语法,对第二个查询使用 NHibernate 标记。
  • 击中数据库两次,然后将结果相交。

tasksFromWorkflow 查询实际上比上面看到的要复杂得多。如果您想查看整个查询,请单击此处。我不确定额外的代码是否真的改变了我的问题——所以我决定在解释问题的同时尽可能缩短立即显示的代码段。

我读到 NHibernate不支持 intersection,所以也许不可能在一个查询中实现而不变得非常复杂?

4

1 回答 1

1

我不知道这会有多好,但这个想法应该很清楚

var tasksFromQueue = DetachedCriteria.For<Task>()
            .Add(Restrictions.Or(
                Subqueries.In("SiteID", DetachedCriteria.For<QueueLocation>().Add(Restrictions.Eq("Queue.ID", queueID)).SetProjection(Projections.Property("ComponentID"))),
                Subqueries.In("OriginalSiteID", DetachedCriteria.For<QueueLocation>().Add(Restrictions.Eq("Queue.ID", queueID)).SetProjection(Projections.Property("ComponentID")))))
            .SetProjection(Projections.Id());

    "Select t from Task t, QueueLocation q where q.Queue.ID = :queueID and (t.SiteID = q.ComponentID or t.OriginalSiteID = q.ComponentID)")
    .SetParameter("queueID", queueID).List<Task>().ToList();

var tasksFromWorkflow = DetachedCriteria.For<Task>()
    .CreateAlias("Order", "order")
    .CreateAlias("TaskDevice", "device")
    .Add(<restrictions>)
    .SetProjection(Projections.Id());

var results = NHibernateSession.CreateCriteria<Task>()
    .Add(Subqueries.In("Id", tasksFromQueue))
    .Add(Subqueries.In("Id", tasksFromWorkflow))
    .List<Task>();
于 2012-10-11T07:44:37.043 回答