Hibernate many to one


many-to-one
使用表為emp和dept
配置文件中配置
<many-to-one name="dept" class="com.wode.entity.Dept" column="deptNo" />

將兩個表關聯起來


完成案例增加和查找


注意在我們使用get的時候,當我們正真去使用連接表數據的時候,才會發出sql語句,這是因為hibernate自動使用了延遲加載。
可以在配置文件中修改
<many-to-one name="dept" class="com.wode.entity.Dept" column="deptNo" lazy="false"/>


我們發現這種方式其實是用了兩個sql語句進行了查找。我們也可以使用一條sal語句來做這個事情。
many-to-one name="dept" class="com.wode.entity.Dept" column="deptNo" lazy="false" fetch="join"/>

Emp emp=(Emp) session.get(Emp.class, 5);
System.out.println(emp.getDept().getDeptNo());
這里要注意的時候,這種做法只對get方法有作用,如果用HQL就沒有用了
  List<Emp> list=session.createQuery("from Emp").list();
  System.out.println(list.get(0).getDept().getDeptNo());
  System.out.println(list.get(1).getDept().getDeptNo());

如果必須要在HQL中使用呢?
  List<Emp> list=session.createQuery("from Emp e left join fetch e.dept").list();
  System.out.println(list.get(0).getDept().getDeptNo());
  System.out.println(list.get(1).getDept().getDeptNo());

 

使用參數根據ID查詢用戶
Query query=session.createQuery("from Emp e where e.empno=?");
  query.setParameter(0, 7654);
  List<Emp> list=query.list();
  for(Emp emp:list){
   System.out.println(emp.getEname());
   System.out.println(emp.getDept().getDname());
  }

 

one -to-many的使用
1:在dept表中進行關系管理
Set<Emp> emps=new HashSet<Emp>();

在配置文件中修改
<set name="emps">
         <key column="deptNo"></key>
         <one-to-many class="com.wode.entity.Emp"/>
</set>

完成查找
Dept dept=(Dept) session.get(Dept.class, 10);
  System.out.println(dept.getDname());
  Set<Emp> sets=dept.getEmps();
  for(Emp emp:sets){
   System.out.println(emp.getEname());
  }


注意這里默認的使用就是延遲加載,為了性能。
我們可以這樣設置
 <set name="emps" lazy="false">

 

完成訂單和訂單條目實驗
order item

案例1:新增
  Order order=new Order();
  order.setCreateDate(new Date());
  
  Item item=new Item();
  item.setProductName("iphone");
  item.setPrice(new BigDecimal("90.90"));
  item.setAmount(2);
  item.setOrder(order);
  
  Item item2=new Item();
  item2.setProductName("ipad");
  item2.setPrice(new BigDecimal("190.90"));
  item2.setAmount(1);
  item.setOrder(order);
  order.getItems().add(item);
  order.getItems().add(item2);
  session.save(order);
  Transaction tx=session.beginTransaction();
  tx.commit();

我們發現報錯了?為什么呢?
 <set name="items" cascade="all">我們需要這樣配置
級聯操作all 代表所有的。當然我們如果只是增加和修改的話可以配置為save-update


這里還可以繼續加入屬性inverse="true" 根據名字我們就能得知,作用是將控制權反轉。最好都是由many方去維護的。想想我們的外鍵建立也是這樣做的。

 

刪除訂單。
  Order order=new Order();
  order.setId(8);
  session.delete(order);
  Transaction transaction=session.beginTransaction();
  transaction.commit();
發現這樣錯誤。在hibernate中必須先去查一次再刪除。
修改
// Order order=new Order();
//  order.setId(8);
//  session.delete(order);
  Order order=(Order) session.get(Order.class, 8);
  session.delete(order);
  Transaction transaction=session.beginTransaction();
  transaction.commit();

這樣就可以了。但是必須要注意的是cascade="all"級聯操作必須這樣做,當然如果只為刪除的話就可以寫成cascade="delete"


實驗:刪除order中的某一個item
 Order order=(Order) session.get(Order.class, 11);
  Set<Item> items=order.getItems();
  System.out.println(items.size());
  Iterator<Item> it=items.iterator();
  while(it.hasNext()){
   if(it.next().getProductName().equals("ipad")){
    it.remove();
   }
  }
  System.out.println(items.size());
  Transaction transaction=session.beginTransaction();
  transaction.commit();

實驗成功,但是數據庫的數據沒有發生改變。

關鍵是級聯
我們修改 <set name="items" cascade="all-delete-orphan" inverse="true">這樣就可以了,那想想cascade的值有哪些呢?

 

 

實驗:通過get獲取order這時候發現, lazy="false"設置延遲加載關閉,發現多次請求
同樣的這里可以這樣設置fetch="join"

 

實驗,查找所有的訂單以及所有訂單里面的條目
@Test
 public void findAll(){
  List<Order> orders=session.createQuery("from Order").list();
  for(Order order:orders){
   System.out.println(order.getCreateDate()+" "+order.getId());
   for(Item item:order.getItems()){
    System.out.println(item.getProductName()+" "+item.getPrice());
   }
  }
 }

發現有多條sql語句,如果我只想一條sql語句怎么辦呢?
再次強調,xml中的fetch只能對get有效的
修改sql語句
List<Order> orders=session.createQuery("from Order o join fetch o.items").list();
但是new question coming??????

修改sql成為
 List<Order> orders=session.createQuery("select distinct(a) from Order a join fetch a.items").list();


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM