NHibernate搜索N + 1期

时间:2011-06-03 16:16:25

标签: nhibernate lucene.net nhibernate.search

我正在使用NHibernate搜索NHibernate 3.0 GA。

我的产品库中有这个代码:

public IList<Product> Find(string term)
        {
            var productFields = new[] { "Name", "Description" };
            var importance = new Dictionary<String, float>(2) { { "Name", 4 }, { "Description", 1 } };
            var analyzer = new StandardAnalyzer();
            var parser = new MultiFieldQueryParser(
                productFields,
                analyzer,
                importance);

            var query = parser.Parse(term);

            var session = Search.CreateFullTextSession(NHibernateSession.Current);
            var tx = session.BeginTransaction();
            var fullTextQuery = session.CreateFullTextQuery(query);
            fullTextQuery.SetFirstResult(0).SetMaxResults(20);
            var results = fullTextQuery.List<Product>();
            tx.Commit();

            return results;
        }

在NH Profiler中,我可以看到为每个找到的产品发出了一个select语句。我错过了什么?

我从2009年发现了this thread,但可能已经修复了这个错误。

编辑[06/06/2011]:

关于协会的我的属性映射如下:

mapping.HasManyToMany(c => c.Categories)
                .Table("CatalogHierarchy")
                .ParentKeyColumn("child_oid")
                .ChildKeyColumn("oid")
                .Cascade.None()
                .Inverse()
                .LazyLoad()
                .AsSet();

            mapping.HasMany(c => c.Variants)
                .Table("CatalogProducts")
                .Where("i_ClassType=2")
                .KeyColumn("ParentOID")
                .Cascade.SaveUpdate()
                .AsSet();

我真的不想急于获取所有类别。

3 个答案:

答案 0 :(得分:1)

由于NHibernate.Search不稳定,我会直接从我的应用程序中使用Lucene.NET(我做了) - 只是向Lucene询问对象的ID,然后使用Session.Load()加载它。

此外,您可以在类映射级别更改LazyLoad设置,而不是在关系级别。 希望它有所帮助。

编辑:您可以为关系指定批量大小,因此它们不会导致选择N + 1问题

答案 1 :(得分:0)

您是否在此方法返回的产品列表中引用任何延迟加载的属性?如果是这样,您可以将属性映射更改为“eager fetch”。

答案 2 :(得分:0)

我最终解决了这个问题。我意识到我没有将整个事情包装成交易。一旦我做了,N + 1问题就消失了。 小学生错误,但是,嘿,你从错误中学习。