linq to sql系列三 延迟加载
首先还是看一下数据表的关系图:
从上图中,香港空间,我们可以发现,tstudent与tclass之间是一对一的关系(需要两张表),而tstudent与tcourse之间是多对多的关系(需要三张表)。
deferredloadingenabled datacontext的deferredloadingenabled属性是指是否需要延时加载,默认值为true。以tstudent为例,其延时加载的对象是指tclass和对应的tcourse。设定延时加载为true时,当访问到tstudent实例的tclass属性或者tstudentcourse属性时会自动加载tclass表和tstudentcourse表中的数据,如下示例代码:
deferrredloading(){using (l2sdbdatacontext db = new l2sdbdatacontext()){//output log on consoledb.log = console.out;db.deferredloadingenabled = true; //default value:true//get a studenttstudent student = db.tstudents.firstordefault();//access property tclass of tstudentconsole.writeline(,student.name,student.tclass.classname);}}
从代码中可以看到,当datacontext的deferredloadingenabled为true时,可以直接访问关系表中的数据。如student.tclass。
输出结果:
从结果我们可以看到,datacontext用到了两段sql,香港服务器,分别从tstudent和tclass中加载数据。如果将datacontext的deferredloadingenabled设为false时,再去访问关系表的数据会抛出空引用的异常。
loadwithloadwith不是datacontext的方法,而是dataloadoptions的方法,可以给datacontext设定 loadoptions属性来改变datacontext加载数据的方式;换句话说是loadoptions设定是否在select主表数据时同时用 join加载关联表的数据。
比如,我要在select tstudent表的时候同时用另一个sql语句把其tclass也select出来,香港服务器,代码如下:
loadwith(){using (l2sdbdatacontext db = new l2sdbdatacontext()){//output log on consoledb.log = console.out;var loadoptions = new dataloadoptions();//设定在load tstudent的时候同时load哪个表loadoptions.loadwith(p=>p.tclass);db.loadoptions = loadoptions;//获取一个studenttstudent student = db.tstudents.firstordefault();//access property tclass of tstudentconsole.writeline(, student.name, student.tclass.classname);}}
输出结果,注意观察生成的sql语句。
这次生成的是一段sql,用到了inner join内联接。
posted on
