C# Nhibernate SetFetchMode-内部连接与左侧外部连接
全部, 我有一个名为Client的实体,它与名为Region的实体有关联,如下所示: 客户->区域 我的所有实体都是延迟加载的(nhibernate默认设置) 客户端中的区域映射为NotNull=false:C# Nhibernate SetFetchMode-内部连接与左侧外部连接,c#,nhibernate,nhibernate-mapping,nhibernate-criteria,C#,Nhibernate,Nhibernate Mapping,Nhibernate Criteria,全部, 我有一个名为Client的实体,它与名为Region的实体有关联,如下所示: 客户->区域 我的所有实体都是延迟加载的(nhibernate默认设置) 客户端中的区域映射为NotNull=false: [ManyToOne(Column = "region_id", ClassType = typeof(Region), NotNull = false)] public virtual Region Region
[ManyToOne(Column = "region_id",
ClassType = typeof(Region),
NotNull = false)]
public virtual Region Region
{
get { return _region; }
set { _region = value; }
}
当我创建客户机条件并设置FetchMode(FetchMode.Join)时,生成的select是一个内部联接,但我期望并保留外部联接,因为区域可以为NULL
上述情况取决于标准的创建方式。如果我像在Ex 1中那样创建标准,我会生成正确的SQL,区域保持外部连接;如果我像在Ex 2中那样创建标准,我会生成错误的SQL,区域保持内部连接
例1)正确的SQL
ICriteria c = s.Session.CreateCriteria<Client>();
c.SetFetchMode("Region", NHibernate.FetchMode.Join);
IList<Client> list2 = c.List<Client>();
SELECT * FROM Companies this_ left outer join Code_Region_Types region2_ on this_.region_id=region2_.entity_id
ICriteria c = s.Session.CreateCriteria<Client>();
ICriteria subC = c.CreateCriteria("Region");
c.SetFetchMode("Region", NHibernate.FetchMode.Join);
IList<Client> list2 = c.List<Client>();
SELECT * FROM Companies this_ inner join Code_Region_Types region1_ on this_.region_id=region1_.entity_id
把join子句搞砸了
这会产生错误的结果,因为某些客户端可能没有区域,因此不包括在查询中
唯一的解决办法似乎是明确指定子条件上的联接:
ICriteria subC = c.CreateCriteria("Region", JoinType.LeftOuterJoin)
上述方法解决了这个问题。这就是Nhibernate所期望的吗?你所经历的绝对正确。你的解决方案真的很合适 呼吁:
criteria.CreateCriteria(associationPath);
实际上,内部是否使用内部联接(请参见):
因此,通过这种方式定义查询。这将是内部连接。然后,取回模式由该标准及其子标准的结果驱动,即只考虑找到的结果
但正如您所发现的,我们可以通过显式调用来改变这一点:
ICriteria subCriteria = criteria
.CreateCriteria(associationPath, JoinType.LeftOuterJoin)
这将达到预期的效果…你所经历的绝对正确。你的解决方案真的很合适 呼吁:
criteria.CreateCriteria(associationPath);
实际上,内部是否使用内部联接(请参见):
因此,通过这种方式定义查询。这将是内部连接。然后,取回模式由该标准及其子标准的结果驱动,即只考虑找到的结果
但正如您所发现的,我们可以通过显式调用来改变这一点:
ICriteria subCriteria = criteria
.CreateCriteria(associationPath, JoinType.LeftOuterJoin)
这将达到预期的效果…你所经历的绝对正确。你的解决方案真的很合适 呼吁:
criteria.CreateCriteria(associationPath);
实际上,内部是否使用内部联接(请参见):
因此,通过这种方式定义查询。这将是内部连接。然后,取回模式由该标准及其子标准的结果驱动,即只考虑找到的结果
但正如您所发现的,我们可以通过显式调用来改变这一点:
ICriteria subCriteria = criteria
.CreateCriteria(associationPath, JoinType.LeftOuterJoin)
这将达到预期的效果…你所经历的绝对正确。你的解决方案真的很合适 呼吁:
criteria.CreateCriteria(associationPath);
实际上,内部是否使用内部联接(请参见):
因此,通过这种方式定义查询。这将是内部连接。然后,取回模式由该标准及其子标准的结果驱动,即只考虑找到的结果
但正如您所发现的,我们可以通过显式调用来改变这一点:
ICriteria subCriteria = criteria
.CreateCriteria(associationPath, JoinType.LeftOuterJoin)
这将达到预期的效果