以Classes[班级]和Student[学生]为例的Demo
//Classes.java public class Classes implements Serializable { private long cid; private String cname; private String cdesc; private Set<Student> students; //get和set }
//Student .java public class Student implements Serializable { private long sid; private String sname; private String sdesc; private Classes classes; //get和set }
1 <?xml version="1.0" encoding="UTF-8"?> 2 <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" 3 "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd"> 4 <hibernate-mapping> 5 <class name="cn.test.testDoubl.Classes" > 6 <id name="cid" type="java.lang.Long" length="5"> 7 <column name="cid"></column> 8 <generator class="increment"></generator> 9 </id> 10 <property name="cname" type="java.lang.String" length="20"></property> 11 <property name="cdesc" type="java.lang.String" length="50"></property> 12 <!-- 13 cascade指的是对象对对象的操作 14 inverse指的是对象对关系的操作 15 --> 16 <set name="students" cascade="all"> 17 <key> 18 <!-- 19 通过classes建立与student之间的联系 20 --> 21 <column name="cid"></column> 22 </key> 23 <one-to-many class="cn.test.testDoubl.Student"/> 24 </set> 25 </class> 26 </hibernate-mapping>
1 <?xml version="1.0" encoding="UTF-8"?> 2 <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" 3 "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd"> 4 <hibernate-mapping> 5 <class name="cn.test.testDoubl.Student"> 6 <id name="sid" type="java.lang.Long" length="5"> 7 <column name="sid"></column> 8 <generator class="increment"></generator> 9 </id> 10 <property name="sname" type="java.lang.String" length="20"></property> 11 <property name="sdesc" type="java.lang.String" length="50"></property> 12 <!-- 13 多对一 14 注意:在many-to-one中没有inverse属性 15 对student表的修改本身就是维护外键 16 --> 17 <many-to-one name="classes" class="cn.test.testDoubl.Classes" cascade="all"> 18 <!-- 19 外键 20 描述了通过student建立与classes之间的联系 21 --> 22 <column name="cid"></column> 23 </many-to-one> 24 </class> 25 </hibernate-mapping>
总结:
当发生transaction.commit的时候,hibernate内部会检查所有的持久化对象 会对持久化对象做一个更新,因为classes是一个持久化状态的对象,所以hibernate 内部要对classes进行更新,因为在classes.hbm.xml文件中<set name="students" cascade="all" inverse="true"> 意味着在更新classes的时候,要级联操作student,而student是一个临时状态的对象 所以要对student进行保存,在保存student的时候,就把外键更新了。
1 package cn.test.testDoubl; 2 3 import java.util.HashSet; 4 import java.util.Set; 5 6 import org.hibernate.Session; 7 import org.hibernate.SessionFactory; 8 import org.hibernate.Transaction; 9 import org.hibernate.cfg.Configuration; 10 import org.junit.Test; 11 12 public class DoTestDoubl { 13 private static SessionFactory sessionFactory; 14 static{ 15 Configuration configuration=new Configuration(); 16 configuration.configure("cn/test/testDoubl/hibernate.cfg.xml"); 17 sessionFactory=configuration.buildSessionFactory(); 18 } 19 20 /** 21 * 1、保存班级 22 * 2、保存学生 23 * 3、保存班级的时候同时保存学生 24 * 4、保存班级的时候同时保存学生,并且建立班级和学生之间的关系 25 * 5、已经存在一个班级,新建一个学生,并且建立该学生和该班级之间的关系 26 * 6、已经存在一个学生,新建一个班级,并且建立该学生和该班级之间的关系 27 * 7、已经存在一个学生,已经存在一个班级,解除该学生和原来班级之间的关系,建立该学生和新班级之间的关系 28 * 8、已经存在一个学生,解除该学生和该学生所在班级之间的关系 29 * 9、解除该班级和所有的学生之间的关系,再重新建立该班级和一些新的学员之间的关系 30 * 10、解除该班级和所有的学生之间的关系 31 * 11、删除班级 32 * * 33 * * 解除该班级和所有的学生之间的关系 34 * * 删除该班级 35 * * 36 * 删除班级的同时删除学生 37 * 12、删除学生 38 * 同删除班级 39 */ 40 41 //3、保存班级的时候同时保存学生 42 /* 43 * Hibernate: select max(cid) from Classes 44 Hibernate: select max(sid) from Student 45 Hibernate: insert into Classes (cname, cdesc, cid) values (?, ?, ?) 46 Hibernate: insert into Student (sname, sdesc, cid, sid) values (?, ?, ?, ?) 47 Hibernate: update Student set cid=? where sid=? 48 */ 49 50 @Test 51 public void testSaveClassesandStudent(){ 52 53 Session session=sessionFactory.openSession(); 54 Transaction transaction=session.beginTransaction(); 55 Student student=new Student(); 56 student.setSname("1111"); 57 student.setSdesc("111111111111"); 58 59 Set<Student> set=new HashSet<Student>(); 60 set.add(student); 61 62 Classes classes=new Classes(); 63 classes.setCname("oo1"); 64 classes.setCdesc("我们都是No。1"); 65 66 classes.setStudents(set); 67 68 session.save(classes); 69 70 transaction.commit(); 71 session.close(); 72 73 } 74 75 76 //4、保存班级的时候同时保存学生,并且建立班级和学生之间的关系 77 /* 78 * Hibernate: select max(sid) from Student 79 Hibernate: select max(cid) from Classes 80 Hibernate: insert into Classes (cname, cdesc, cid) values (?, ?, ?) 81 Hibernate: insert into Student (sname, sdesc, cid, sid) values (?, ?, ?, ?) 82 */ 83 @Test 84 public void testSaveClassesandStudent2(){ 85 86 Session session=sessionFactory.openSession(); 87 Transaction transaction=session.beginTransaction(); 88 89 Student student=new Student(); 90 student.setSname("1111"); 91 student.setSdesc("111111111111"); 92 93 Classes classes=new Classes(); 94 classes.setCname("oo1"); 95 classes.setCdesc("我们都是No。1"); 96 97 student.setClasses(classes);//通过student来维护classes 98 //对student的增、删、改本身就是对外键的操作,所以这里不再发出update语句 99 //一对多,多的一方维护关系,效率比较高 100 101 session.save(student); 102 103 transaction.commit(); 104 session.close(); 105 106 } 107 108 //5、已经存在一个班级,新建一个学生,并且建立该学生和该班级之间的关系 109 /* 110 * Hibernate: select classes0_.cid as cid0_0_, classes0_.cname as cname0_0_, classes0_.cdesc as cdesc0_0_ from Classes classes0_ where classes0_.cid=? 111 Hibernate: select max(sid) from Student 112 Hibernate: insert into Student (sname, sdesc, cid, sid) values (?, ?, ?, ?) 113 */ 114 @Test 115 public void testSaveStudentToClasses(){ 116 Session session =sessionFactory.openSession(); 117 Transaction transaction=session.beginTransaction(); 118 119 Classes classes=(Classes) session.get(Classes.class, 1L); 120 121 Student student=new Student(); 122 student.setSname("王尼玛"); 123 student.setSdesc("暴走漫画,就是劲爆"); 124 student.setClasses(classes); 125 126 session.save(student); 127 128 transaction.commit(); 129 session.close(); 130 } 131 132 //6、已经存在一个学生,新建一个班级,并且建立该学生和该班级之间的关系 133 /* 134 * Hibernate: select student0_.sid as sid1_0_, student0_.sname as sname1_0_, student0_.sdesc as sdesc1_0_, student0_.cid as cid1_0_ from Student student0_ where student0_.sid=? 135 Hibernate: select max(cid) from Classes 136 Hibernate: insert into Classes (cname, cdesc, cid) values (?, ?, ?) 137 Hibernate: update Student set sname=?, sdesc=?, cid=? where sid=? 138 */ 139 @Test 140 public void testSaveClassesToStudent(){ 141 Session session=sessionFactory.openSession(); 142 Transaction transaction=session.beginTransaction(); 143 144 Student student=(Student) session.get(Student.class, 1L); 145 146 Classes classes=new Classes(); 147 classes.setCname("黑客集训"); 148 classes.setCdesc("里面都是牛人"); 149 150 student.setClasses(classes); 151 152 session.save(classes); 153 154 transaction.commit(); 155 session.close(); 156 } 157 158 //7、已经存在一个学生,已经存在一个班级,解除该学生和原来班级之间的关系,建立该学生和新班级之间的关系 159 /* 160 * Hibernate: select classes0_.cid as cid0_0_, classes0_.cname as cname0_0_, classes0_.cdesc as cdesc0_0_ from Classes classes0_ where classes0_.cid=? 161 Hibernate: select student0_.sid as sid1_0_, student0_.sname as sname1_0_, student0_.sdesc as sdesc1_0_, student0_.cid as cid1_0_ from Student student0_ where student0_.sid=? 162 Hibernate: update Student set sname=?, sdesc=?, cid=? where sid=? 163 */ 164 @Test 165 public void testToRebuild(){ 166 Session session=sessionFactory.openSession(); 167 Transaction transaction=session.beginTransaction(); 168 169 Classes classes=(Classes) session.get(Classes.class, 1L); 170 Student student=(Student) session.get(Student.class, 1L); 171 student.setClasses(classes); 172 transaction.commit(); 173 session.close(); 174 } 175 176 //8、已经存在一个学生,解除该学生和该学生所在班级之间的关系 177 /* 178 * Hibernate: select student0_.sid as sid1_0_, student0_.sname as sname1_0_, student0_.sdesc as sdesc1_0_, student0_.cid as cid1_0_ from Student student0_ where student0_.sid=? 179 Hibernate: update Student set sname=?, sdesc=?, cid=? where sid=? 180 */ 181 @Test 182 public void testToRomove(){ 183 Session session=sessionFactory.openSession(); 184 Transaction transaction=session.beginTransaction(); 185 186 Student student=(Student) session.get(Student.class, 1L); 187 student.setClasses(null); 188 189 transaction.commit(); 190 session.close(); 191 } 192 193 //9、解除该班级和所有的学生之间的关系,再重新建立该班级和一些新的学员之间的关系 194 /* 195 * Hibernate: select classes0_.cid as cid0_0_, classes0_.cname as cname0_0_, classes0_.cdesc as cdesc0_0_ from Classes classes0_ where classes0_.cid=? 196 Hibernate: select students0_.cid as cid0_1_, students0_.sid as sid1_, students0_.sid as sid1_0_, students0_.sname as sname1_0_, students0_.sdesc as sdesc1_0_, students0_.cid as cid1_0_ from Student students0_ where students0_.cid=? 197 Hibernate: select max(sid) from Student 198 Hibernate: insert into Student (sname, sdesc, cid, sid) values (?, ?, ?, ?) 199 Hibernate: insert into Student (sname, sdesc, cid, sid) values (?, ?, ?, ?) 200 Hibernate: update Student set sname=?, sdesc=?, cid=? where sid=? 201 Hibernate: update Student set sname=?, sdesc=?, cid=? where sid=? 202 Hibernate: update Student set sname=?, sdesc=?, cid=? where sid=? 203 Hibernate: update Student set sname=?, sdesc=?, cid=? where sid=? 204 Hibernate: update Student set cid=? where sid=? 205 Hibernate: update Student set cid=? where sid=? 206 */ 207 @Test 208 public void testremoveAndRebuild(){ 209 Session session=sessionFactory.openSession(); 210 Transaction transaction=session.beginTransaction(); 211 212 Classes classes=(Classes) session.get(Classes.class, 2L); 213 Set<Student> students=classes.getStudents(); 214 for(Student student:students) 215 { 216 student.setClasses(null); 217 } 218 219 Student student=new Student(); 220 student.setSname("新建1"); 221 student.setSdesc("新建轩辕rtyuio"); 222 Student student2=new Student(); 223 student2.setSname("新建2"); 224 student2.setSdesc("新建轩sdfghyujikol;辕rtyuio"); 225 226 students.add(student); 227 students.add(student2); 228 229 transaction.commit(); 230 session.close(); 231 } 232 233 //10、解除该班级和所有的学生之间的关系 234 @Test 235 public void testRemoveAllStudents(){ 236 Session session=sessionFactory.openSession(); 237 Transaction transaction=session.beginTransaction(); 238 239 Classes classes=(Classes) session.get(Classes.class, 2L); 240 Set<Student> students= classes.getStudents(); 241 for(Student student:students){ 242 student.setClasses(null); 243 } 244 transaction.commit(); 245 session.close(); 246 } 247 248 //11、删除班级 249 //先解除关系,再删除班级 250 @Test 251 public void testDeleteClasses(){ 252 Session session=sessionFactory.openSession(); 253 Transaction transaction=session.beginTransaction(); 254 255 Classes classes=(Classes) session.get(Classes.class, 1L); 256 Set<Student> set=classes.getStudents(); 257 for(Student student:set){ 258 student.setClasses(null); 259 } 260 session.delete(classes); 261 transaction.commit(); 262 session.close(); 263 } 264 265 //在删除班级的时候,同时删除整个班级的学生 266 267 @Test 268 public void testDeleteClasses2(){ 269 Session session=sessionFactory.openSession(); 270 Transaction transaction=session.beginTransaction(); 271 272 Classes classes=(Classes) session.get(Classes.class, 2L); 273 Set<Student> set=classes.getStudents(); 274 for(Student student:set){ 275 student.setClasses(null); 276 break; 277 } 278 //session.delete(classes); 279 transaction.commit(); 280 session.close(); 281 } 282 283 }