请注明转载地址:http://www.cnblogs.com/arhat

通过上一章的学习,我们建立了Student和Clazz之间的关联属性,并从Student(many)的一方查看了Clazz的信息,同时我们使用了懒加载技术和立即执行的方式来实现了对象的关联查询,那么在本章中,我们继续来研究“多对一,一对多,懒加载”的问题。

在本章中,我们从Clazz(one端)来发送查询请求,查询一下班级中Student学生信息。首先呢,我们把上一届中的两个映射文件的内容更改一下,让它启用一下懒加载,即把lazy设置为true或着是去掉(默认情况下,NHibernate是开启懒加载的)。

然后我们来查询一下班级为1的班级名称和这个班级中所有学生的信息。现在,我们添加一个D_Clazz类,内容如下:

public class D_Clazz
{ public Model.Clazz GetClazz(int id) { ISession session = NHibernateHelper.OpenSession(); return session.Get<Model.Clazz>(id); } }

更改一下主程序的代码,注意这里需要在主程序中添加Iesi.Collection.dll的引用。

static void Main(string[] args)
{ DAL.D_Clazz dal = new DAL.D_Clazz(); Model.Clazz clazz=dal.GetClazz(); Console.WriteLine(); Console.WriteLine("班级名称:" + clazz.CName); Console.WriteLine(); foreach (Model.Student student in clazz.Students) { Console.WriteLine("学生:"+student.SName); Console.WriteLine(); }
}

好,现在我们来运行一下,看看运行的结果如何。

我们已经成功的使用懒加载来查询出Clazz关联的属性。从上面的结果来看,NHibernate发出了两条SQL语句。当让这个懒加载之所以能够成功的查询,是因为我们没有释放ISession的资源。那么现在我们不适用懒加载来查询一下,看看有什么区别没有!我们更改一下D_Clazz的代码:

public Model.Clazz GetClazz(int id) 

  {

//ISession session = NHibernateHelper.OpenSession();

//return session.Get<Model.Clazz>(id);

using (ISession session = NHibernateHelper.OpenSession())

            {

return session.Get<Model.Clazz>(id);

            }
}

同时我们更改Clazz.hbm.xml,把<Set>的懒加载去掉,也就是lazy=false。

<set name="Students" table="student" lazy="false">

            <key column="Cid"></key>

            <one-to-many class="Model.Student"/>
</set>

然后运行一下程序看看结果。

此时,我们发现,当使用“立即执行”的时候,NHibernate会发出两条SQL语句,而这两条SQL语句是同时执行的和上面懒加载相比,是不是影响效率了呢?上面懒加载的时候,是当我们需要的时候,才发出第二条语句,而“立即执行”是不管你有没有用,我全部给你查询出来。大家可以试想一下,这样不就是浪费我们昂贵的内存资源吗?如果用得上的话那就不说什么了,问题如果我们用不上则不久白白浪费我们的资源了嘛!

而且在我们传统的思想中,我们应该是使用完资源后要立即释放,但是要使用NHibernate懒加载的时候却要求不能释放资源,这个不就是矛盾嘛。这个该怎么办呢?幸运的是,NHiberante为我们提供了一个NHibernateUtil的工具类,这个工具类中有一个方法非常的游泳,就是Initializ方法,这个方法是使用一个代理来帮我们初始化未初始化的对象。有个这个方法,我们就可以两者兼得了,既可以使用懒加载,也可以释放ISession资源。首先,我们下把hbm.xml中的lazy=false全部去掉。然后改写一下D_Clazz的代码:

public Model.Clazz GetClazz(int id)
{ //ISession session = NHibernateHelper.OpenSession(); //return session.Get<Model.Clazz>(id); using (ISession session = NHibernateHelper.OpenSession()) { Model.Clazz clazz = session.Get<Model.Clazz>(id); NHibernateUtil.Initialize(clazz.Students); return clazz; } }

我们在得到Clazz对象的时候,并没有急着返回,而是使用了NHibernateUtil.Initialize方法来初始化Students这个集合。然后在返回clazz对象,此时的clazz对象中就有了Students这个集合对象了。

下面是运行的结果图,发现和使用lazy=false的效果是一样的。

其实,NHiberante在懒加载的问题上真是个头疼的问题,就好比鱼和熊掌不能兼得,要么使用懒加载但是不能及时的释放对象,要么就是使用“立即执行”占用大量的资源。

在NHibernate中,其实提到一个这种的办法就是使用Open Session In View的概念,只不过这概念只能在Web应用程序中才能用,如果是Winform的话,不好意思,老魏还这没找到一个合适的方法。不过老魏相信后续的NHibernate可能会解决这个问题的。

所以在使用NHibernate的时候,什么时候使用懒加载,什么时候不使用是个非常重要的问题。

一步步学习NHibernate(5)——多对一,一对多,懒加载(2)的更多相关文章

  1. 一步步学习NHibernate(4)——多对一,一对多,懒加载(1)

    请注明转载地址:http://www.cnblogs.com/arhat 通过上一章的学习,我们学会如何使用NHibernate对数据的简单查询,删除,更新和插入,那么如果说仅仅是这样的话,那么NHi ...

  2. MyBatis --- 映射关系【一对一、一对多、多对多】,懒加载机制

    映射(多.一)对一的关联关系 1)若只想得到关联对象的id属性,不用关联数据表 2)若希望得到关联对象的其他属性,要关联其数据表 举例: 员工与部门的映射关系为:多对一 1.创建表 员工表 确定其外键 ...

  3. 【IOS学习基础】weak和strong、懒加载、循环引用

    一.weak和strong 1.理解 刚开始学UI的时候,对于weak和strong的描述看得最多的就是“由ARC引入,weak相当于OC中的assign,但是weak用于修饰对象,但是他们都不会造成 ...

  4. webpack学习笔记—优化缓存、合并、懒加载等

    除了前面的webpack基本配置,还可以进一步添加配置,优化合并文件,加快编译速度.下面是生产环境配置文件webpack.production.js,与wenbpack.config.js相比其不需要 ...

  5. 一步步学习NHibernate(6)——ISession的管理

    请注明转载地址:http://www.cnblogs.com/arhat 今天老魏那个汗啊,我的ThinkPad的电源线不通电了,擦啊.明天还得掏银子买一个!心疼啊,原装的啊.不过话说回来,已经用了将 ...

  6. 一步步学习NHibernate(8)——HQL查询(2)

    请注明转载地址:http://www.cnblogs.com/arhat 在上一章中,老魏带着大家学习了HQL语句,发现HQL语句还是非常不错的,尤其是在懒加载的时候,书写起来比较的舒服,但是这里老魏 ...

  7. EF Code First 一对多、多对多关联,如何加载子集合?

    应用场景 先简单描述一下标题的意思:使用 EF Code First 映射配置 Entity 之间的关系,可能是一对多关系,也可能是多对多关系,那如何加载 Entity 下关联的 ICollectio ...

  8. MyBatis加强(1)~myBatis对象关系映射(多对一关系、一对多关系)、延迟/懒加载

    一.myBatis对象关系映射(多对一关系.一对多关系) 1.多对一关系: ---例子:多个员工同属于一个部门. (1)myBatis发送 额外SQL: ■ 案例:员工表通过 dept_id 关联 部 ...

  9. 【Java EE 学习 47】【Hibernate学习第四天】【sesion】【一级缓存】【懒加载】

    一.Session概述 1.Session 接口是 Hibernate 向应用程序提供的操纵对数据库的最主要的接口, 它提供了基本的保存, 更新, 删除和加载Java 对象的方法. 2.理解Sessi ...

随机推荐

  1. SQL Abstraction and Object Hydration

    SQL Abstraction and Object Hydration In the last chapter, we introduced database abstraction and a n ...

  2. IPC:shared memory

    #include <stdio.h> #include <sys/shm.h> #include <sys/stat.h> int main () { int se ...

  3. typedef的使用3——使用经过typedef定义的函数构成的函数数组

    #include <stdio.h> #include <string.h>//不加还能跑,加上反而跑不了了...笑哭 #pragma warning(disable:4996 ...

  4. spring+ibatis环境搭建

    简单的spring+ibatis入门实例:ibatis是一种半自动化的持久层框架,它介于JDBC和hibernate之间,使用比较灵活. 一:目录结构 二:需要导入的jar包: 所有的第三方jar包都 ...

  5. hdf5 api

    https://www.physics.ohio-state.edu/~wilkins/computing/HDF/hdf5tutorial/index.html

  6. dig命令浅析

    dig命令,功能更强大的命令. man dig dig [@server] [-b address] [-c class] [-f filename] [-k filename] [-m] \ [-p ...

  7. 在orangepi-PC, ubuntu mini下使用usb wifi(rtl8188cu/rtl8192cu)

    本文章针对orangepi-pc下的ubuntu,分两部分,分别介绍在ubuntu14.04(trusty)mini下使用usb无线网卡的方式,以及怎样在ubuntu15.10(wily)mini下正 ...

  8. Ext.Net学习笔记20:Ext.Net FormPanel 复杂用法

    Ext.Net学习笔记20:Ext.Net FormPanel 复杂用法 在上一篇笔记中我们介绍了Ext.Net的简单用法,并创建了一个简单的登录表单.今天我们将看一下如何更好是使用FormPanel ...

  9. OC中 block 的用法

    block 常用于反向传值 声明 返回值类型 (^block)(参数列表) 调用 闭包的名字=^(参数列表){}: 闭包的名字(): 如: void(^aaaaa)(int num,NSString ...

  10. C#上传图片和生成缩略图以及图片预览

    因工作需要,上传图片要增加MIME类型验证和生成较小尺寸的图片用于浏览.根据网上代码加以修改做出如下效果图: 前台代码如下: <html xmlns="http://www.w3.or ...