, " ", . "" ? ( , ) SQL- ( ) ?
1: , ( , ). ( , - 200).
:
var items = session.Query<Work>()
.Fetch(c => c.ParentWork)
.Fetch(c => c.ChildWorks).ToList();
var item = session.Get<Work>(id);
SQL-, . item (, , ..).
2: . .
NHibernate , , . N + 1, , 1 ( ).
, :
var item = session.Get<Work>(id);
Work parent = item.ParentWork;
Work root = item;
while (parent != null)
{
root = parent;
parent = parent.ParentWork;
}
this.ScanChildren(root);
private void ScanChildren(Work item)
{
if (item == null)
{
return;
}
foreach (Work child in item.ChildWorks)
{
string name = child.Name;
this.ScanChildren(child);
}
}
Edit:
3: . .
, , .
var work = repo.Session.Get<Work>(id);
Work parent = work.ParentWork;
Work root = work;
while (parent != null)
{
root = parent;
parent = parent.ParentWork;
}
IList<Work> worksAll = new List<Work>() { root };
IList<Work> worksPerLevel = new List<Work>() { root };
int count = worksPerLevel.Count;
while (count > 0)
{
worksPerLevel = this.GetChildren(session, worksPerLevel);
worksPerLevel.ForEach(c => worksAll.Add(c));
count = worksPerLevel.Count;
}
foreach (Work c in worksAll)
{
string s = c.Name;
}
private IList<Work> GetChildren(ISession session, IList<Work> worksPerLevel)
{
IList<Work> result = new List<Work>();
IList<int> ids = worksPerLevel.Select(c => c.Id).ToList();
result = session.QueryOver<Work>()
.Where(
NHibernate.Criterion.Restrictions.InG<int>(
NHibernate.Criterion.Projections.Property<Work>(
c => c.ParentWork.Id),
ids)
)
.Fetch(c => c.ChildWorks).Eager
.List();
return result;
}
N + 1, , NHibernate DB . x + y, x - , Work, y - ( ).