hibernate的多对多的关联 2(增加、删除)

重点:

1、级联新增 inverse属性值的设置
2、 级联删除
重点解析:

1.hibernate的多对多
1.1 hibernate可以直接映射多对多关联关系(看作两个一对多)
讲解inverse;
总共四种 (false 是控制方 ,true 是被控制方),其中有两种正确,两种错误

  • 1、book:false category:true ✓(代表意思是:将维护的责任交给book)
  • 2、book: true category:false ✓
  • 3、book:true category:true ✗
  • 4、book:false category:false ✗

多对多关系注意事项
2.1 一定要定义一个主控方
2.2 多对多删除
2.2.1 主控方直接删除
2.2.2 被控方先通过主控方解除多对多关系,再删除被控方
2.2.3 禁用级联删除
2.3 关联关系编辑,不需要直接操作桥接表,hibernate的主控方会自动维护

这是是dao方法的增加(之前的实体类还有配置文件在前几天发布了)
// 书籍新增
	public Integer add(Book book) {
		Configuration configure = new Configuration().configure("hibernate.cfg.xml");
		SessionFactory sessionFactory = configure.buildSessionFactory();
		Session session = sessionFactory.openSession();
		Transaction transaction = session.beginTransaction();
		Integer bid = (Integer) session.save(book);
		transaction.commit();
		session.close();
		return bid;
	}
	
	
	//书籍删除
		public void del(Book book) {
			Configuration configure = new Configuration().configure("hibernate.cfg.xml");
		SessionFactory sessionFactory = configure.buildSessionFactory();
		Session session = sessionFactory.openSession();
		Transaction transaction = session.beginTransaction();
			session.delete(book);
			transaction.commit();
		session.close();
		}


//  书籍类型 新增
		public Integer save(Category category) {
			Configuration configure = new Configuration().configure("hibernate.cfg.xml");
		SessionFactory sessionFactory = configure.buildSessionFactory();
		Session session = sessionFactory.openSession();
		Transaction transaction = session.beginTransaction();
			Integer cid = (Integer) session.save(category);
			transaction.commit();
		session.close();
			return cid;
		}
	
		/**
		 * 因为被控方被中间表所引用
		 * 1、触发关联关系(主控方解除多对多关系)
		 * 2、删除主控方的相关数据
		 * 
		 * @param category
		 */


		// 书籍类型删除
		public void del(Category category) {
			Configuration configure = new Configuration().configure("hibernate.cfg.xml");
		SessionFactory sessionFactory = configure.buildSessionFactory();
		Session session = sessionFactory.openSession();
		Transaction transaction = session.beginTransaction();
			Category c = session.get(Category.class, category.getCategoryId());
			//c 里面保存着与某一些书籍相关联的关系
			for (Book b : c.getBooks()) {
				//注意:关系交于book维护
//				c.getBooks().remove(b);   这是错误的
				
				b.getCategories().remove(c);
			}
			session.delete(c);
			transaction.commit();
		session.close();
		}

测试的方法,代码分享:

/**----------------------------------six---------------------------
	 *- 提交书本信息,勾选复选框类别, 提交
	 * jdbc: bookDao.add,bookCategoryDao.add
	 * hibernate :  bookDao.add
	 * 
	 * 讲解inverse;
	 * 总共四种  (false 是控制方   ,true 是被控制方),其中有两种正确,两种错误
	 * 1、book:false   category:true		✓(代表意思是:将维护的责任交给book)
	 * 2、book: true   category:false		✓
	 * 3、book:true   category:true  		✗
	 * 4、book:false   category:false 		✗
	 */
	
	
	/*错误1:
	 * Caused by: com.mysql.jdbc.exceptions.
	 * jdbc4.MySQLIntegrityConstraintViolationException:
	 *  Column 'category_name' cannot be null
	 *  
	 *  解决方法:这个错误是没有把对象持久态,所以才会出现这个问题把对象通过get方法获取对象持久态就没问题了
	 *  
	 *  */
	
	
	
	/**
	 * 注意:
	 * hibernate 通过管理持久态对象来操作数据库
	 */
	@Test
	public void testAdd() {
		/**
		 * 1、book:false   category:true	✓(代表意思是:将维护的责任交给book)
		 */
		Book book = new Book();
		book.setBookName("颤抖吧!ET");
		book.setPrice(66F);
		
		//这是错误的示范
		Category category = new Category();
		category.setCategoryId(4);
		book.getCategories().add(category);
		
		//要通过get获取持久态对象
		/*Category category = new Category();
		category.setCategoryId(4);
		book.getCategories().add(this.categoryDao.get(category));*/
		 this.bookDao.add(book);
	}
	
	
	/*
	 * 在新增类别的时候不能用第一种维护关系,必须所以第二种,因为(将关系(中间表)维护的责任交给book))
	 * 2、book: true   category:false		✓
	 * 
	 */
	@Test
	public void testAdd2() {
		Category category = new Category();
		category.setCategoryName("穿越");
		Book book = new Book();
		book.setBookId(4);
		category.getBooks().add(this.bookDao.get(book));
		this.categoryDao.save(category);
	}
	/**
	 * 3、book:true   category:true  		✗
	 * 出现错误:中间表无对象维护(类别新增但是中间没有数据)
	 */
	@Test
	public void testAdd3() {
		Category category = new Category();
		category.setCategoryName("言情");
		Book book = new Book();
		book.setBookId(5);
		category.getBooks().add(this.bookDao.get(book));
		this.categoryDao.save(category);
	}
	
	
	/**
	 * 4、book:false   category:false 		✗
	 * 相同的数据加入就会在中间表中有重复的数据,
	 * 到时候在查询的时候会重复的数据
	 * 
	 */

在这里插入图片描述

/**------------------del----------------------
	 *  多对多删除
	 * 1 、主控方直接删除
	 * 2、 被控方先通过主控方解除多对多关系,再删除被控方
	 */
	
	/*
	 * 主控方直接删除
	 * 结论: 一并将从表关联的中间表信息删除
	 */
	@Test
	public void testDel() {
		Book book = new Book();
		book.setBookId(5);
		this.bookDao.del(book);
	}
	
	/*
	 * 被控方先通过主控方解除多对多关系,再删除被控方
	 */
	
	
	/**
	 * 错误2:
	 * Caused by: com.mysql.jdbc.exceptions.jdbc4.MySQLIntegrityConstraintViolationException: 
	 * Cannot delete or update a parent row: a foreign key constraint fails 
	 * (`mybatis_ssm`.`t_hibernate_book_category`, CONSTRAINT `t_hibernate_book_category_ibfk_2` 
	 * FOREIGN KEY (`cid`) REFERENCES `t_hibernate_category` (`category_id`))
	 * 
	 * 解决方法:
	 * 这是报数据库的主外键连接的错误,如果你有删除的外键表的数据就要先删除主键表的数据
	 */
	
	@Test
	public void testDel2() {
		Category category = new Category();
		category.setCategoryId(1);
		this.categoryDao.del(category);
	}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值