标签:hibernate
基本需求是:一个项目可以有多个开发人员,一个开发人员可以参加多个项目,因此项目和开发人员是多对多的关系。本文中的学习重点,还和前几篇文章一样,都是JavaBean类的映射文件中的配置。
Project.java
package com.rk.hibernate.h_many2many;
import java.util.Set;
public class Project
{
	private int prjId;
	private String prjName;
	private Set<Developer> devps;
	public int getPrjId()
	{
		return prjId;
	}
	public void setPrjId(int prjId)
	{
		this.prjId = prjId;
	}
	public String getPrjName()
	{
		return prjName;
	}
	public void setPrjName(String prjName)
	{
		this.prjName = prjName;
	}
	public Set<Developer> getDevps()
	{
		return devps;
	}
	public void setDevps(Set<Developer> devps)
	{
		this.devps = devps;
	}
}Project.hbm.xml
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> <hibernate-mapping package="com.rk.hibernate.h_many2many" auto-import="true"> <class name="Project" table="T_Project"> <id name="prjId" column="id"> <generator class="native"></generator> </id> <property name="prjName" column="name"></property> <set name="devps" table="R_Project_Developer" inverse="true" cascade="save-update"> <key column="prjId"></key> <many-to-many column="devpId" class="Developer"></many-to-many> </set> </class> </hibernate-mapping>
Developer.java
package com.rk.hibernate.h_many2many;
import java.util.Set;
public class Developer
{
	private int devpId;
	private String devpName;
	private Set<Project> prjs;
	public int getDevpId()
	{
		return devpId;
	}
	public void setDevpId(int devpId)
	{
		this.devpId = devpId;
	}
	public String getDevpName()
	{
		return devpName;
	}
	public void setDevpName(String devpName)
	{
		this.devpName = devpName;
	}
	public Set<Project> getPrjs()
	{
		return prjs;
	}
	public void setPrjs(Set<Project> prjs)
	{
		this.prjs = prjs;
	}
	@Override
	public String toString()
	{
		return "Developer [devpId=" + devpId + ", devpName=" + devpName + "]";
	}
	
}Developer.hbm.xml
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE hibernate-mapping PUBLIC "-//Hibernate/Hibernate Mapping DTD 3.0//EN" "http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd"> <hibernate-mapping package="com.rk.hibernate.h_many2many" auto-import="true"> <class name="Developer" table="T_Developer"> <id name="devpId" column="id"> <generator class="native"></generator> </id> <property name="devpName" column="name"></property> <set name="prjs" table="R_Project_Developer"> <key column="devpId"></key> <many-to-many column="prjId" class="Project"></many-to-many> </set> </class> </hibernate-mapping>
App.java
package com.rk.hibernate.h_many2many;
import java.util.HashSet;
import java.util.Set;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.classic.Session;
import org.junit.Test;
public class App
{
	private static SessionFactory sf;
	static
	{
		sf = new Configuration()
				.configure()
				.addClass(Project.class)
				.addClass(Developer.class)
				.buildSessionFactory();
	}
	
	// 1. 多对多,保存  【只能通过一方维护另外一方,不能重复维护!】
	@Test
	public void testSave()
	{
		int i = 0;
		Session session = sf.openSession();
		session.beginTransaction();
		
		// 创建项目对象
		Project prj1 = new Project();
		prj1.setPrjName("AO项目" + i);
		
		Project prj2 = new Project();
		prj2.setPrjName("电商项目" + i);
		
		// 创建开发人员对象
		Developer devp1 = new Developer();
		devp1.setDevpName("张三" + i);
		Developer devp2 = new Developer();
		devp2.setDevpName("李四" + i);
		Developer devp3 = new Developer();
		devp3.setDevpName("王五" + i);
		
		// 关系 【项目方来维护】
		Set<Developer> set1 = new HashSet<Developer>();
		set1.add(devp1);
		set1.add(devp2);
		
		Set<Developer> set2 = new HashSet<Developer>();
		set2.add(devp2);
		set2.add(devp3);
		
		prj1.setDevps(set1);
		prj2.setDevps(set2);
		
		// 保存
		session.save(devp1);
		session.save(devp2);
		session.save(devp3);
		
		session.save(prj1);
		session.save(prj2);
		
		session.getTransaction().commit();
		session.close();
		System.out.println("执行结束!");
	}
	
}| 序号 | 操作类型 | 是否影响 | 具体说明 | 
|---|---|---|---|
| 1 | 保存数据 | 有影响 | inverse=false ,有控制权,可以维护关联关系; 保存数据的时候会把对象关系插入中间表; inverse=true, 没有控制权, 不会往中间表插入数据。 | 
| 2 | 获取数据 | 无 | 获取数据只是参照中间表中保存的关系,并不会对这种关系进行修改,因此获取数据不会受到影响。 | 
| 3 | 解除关联关系 | 有影响 | inverse=false ,有控制权, 解除关系就是删除中间表的数据。 inverse=true, 没有控制权,不能解除关系。 | 
| 4 | 删除数据 | 有影响 | inverse=false, 有控制权。 先删除中间表数据,再删除自身。 inverse=true, 没有控制权。 如果删除的数据有被引用,会报错! 否则,才可以删除 | 
App_Inverse.java
package com.rk.hibernate.h_many2many;
import java.util.HashSet;
import java.util.Set;
import org.hibernate.SessionFactory;
import org.hibernate.cfg.Configuration;
import org.hibernate.classic.Session;
import org.junit.Test;
public class App_Inverse
{
	private static SessionFactory sf;
	static
	{
		sf = new Configuration()
				.configure()
				.addClass(Project.class)
				.addClass(Developer.class)
				.buildSessionFactory();
	}
	
	// 多对多
	//1. 设置inverse属性,对保存数据影响?
	// 有影响。
	// inverse=false ,有控制权,可以维护关联关系; 保存数据的时候会把对象关系插入中间表;
	// inverse=true,  没有控制权, 不会往中间表插入数据。
	@Test
	public void testSave()
	{
		int i = 6;
		Session session = sf.openSession();
		session.beginTransaction();
		
		// 创建项目对象
		Project prj1 = new Project();
		prj1.setPrjName("AO项目" + i);
		
		Project prj2 = new Project();
		prj2.setPrjName("电商项目" + i);
		
		// 创建开发人员对象
		Developer devp1 = new Developer();
		devp1.setDevpName("张三" + i);
		Developer devp2 = new Developer();
		devp2.setDevpName("李四" + i);
		Developer devp3 = new Developer();
		devp3.setDevpName("王五" + i);
		
		// 关系 【项目方来维护】
		Set<Developer> set1 = new HashSet<Developer>();
		set1.add(devp1);
		set1.add(devp2);
		
		Set<Developer> set2 = new HashSet<Developer>();
		set2.add(devp2);
		set2.add(devp3);
		
		prj1.setDevps(set1);
		prj2.setDevps(set2);
		
		// 保存
//		session.save(devp1);
//		session.save(devp2);
//		session.save(devp3);
		
		session.save(prj1);		//上面的三条语句注释掉后,如果想保存成功,必须要设置级联保存 
		session.save(prj2);
		
		session.getTransaction().commit();
		session.close();
		System.out.println("执行结束!");
	}
	
	//2 .设置inverse属性, 对获取数据影响?  无
	@Test
	public void testGet()
	{
		Session session = sf.openSession();
		session.beginTransaction();
		
		Project prj = (Project) session.get(Project.class, 3);
		System.out.println(prj.getPrjName());
		System.out.println(prj.getDevps());
		
		session.getTransaction().commit();
		session.close();
		System.out.println("执行结束!");
	}
	//3. 设置inverse属性, 对解除关系影响?
	// 有影响。
	// inverse=false ,有控制权, 解除关系就是删除中间表的数据。
	// inverse=true, 没有控制权,不能解除关系。
	@Test
	public void testClearRelation()
	{
		Session session = sf.openSession();
		session.beginTransaction();
		
		Project prj = (Project) session.get(Project.class, 3);
		prj.getDevps().clear();
		
		session.getTransaction().commit();
		session.close();
		System.out.println("执行结束!");
	}
	
	//4. 设置inverse属性,对删除数据的影响?
	// inverse=false, 有控制权。 先删除中间表数据,再删除自身。
	// inverse=true, 没有控制权。 如果删除的数据有被引用,会报错! 否则,才可以删除
	@Test
	public void testDelete()
	{
		Session session = sf.openSession();
		session.beginTransaction();
		
		Project prj = (Project) session.get(Project.class, 13);
		if(prj != null)
		{
			session.delete(prj);
		}
		
		session.getTransaction().commit();
		session.close();
		System.out.println("执行结束!");
	}
}标签:hibernate
原文地址:http://lsieun.blog.51cto.com/9210464/1825920