Hibernate 비관 자물쇠 와 낙관 자물쇠 실례 상세 설명
비관 적 자물쇠
비관 적 인 자 물 쇠 는 보통 데이터 베이스 체제 에 의 해 이 루어 집 니 다.전체 과정 에서 데 이 터 를 잠 그 고(조회 할 때)사물 이 풀 리 지 않 으 면 그 어떠한 사용자 도 보 거나 수정 할 수 없습니다.
다음은 하나의 사례 를 통 해 설명 하 겠 습 니 다.
사례:화물 재고 가 1000 이 라 고 가정 하고 계산 원 1 이 데 이 터 를 꺼 내 수정 을 준 비 했 으 나 잠시 일이 있어 가 버 렸 다.그 동안 채산 원 2 는 데 이 터 를 꺼 내 200 을 빼 고 채산 원 1 이 돌 아 왔 다.방금 꺼 낸 수량 을 200 을 빼 면 문제 가 생 겼 다.채산 원 1 은 800 을 바탕 으로 수정 하지 않 았 다.이른바 업데이트 분실 이라는 비관 적 인 자물쇠 로 해결 할 수 있다.
Inventory.java:
public class Inventory {
/* */
private String itemNo;
/* */
private String itemName;
/* */
private int quantity;
// setter getter
}
Inventory.hbm.xml:
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<class name="com.lixue.bean.Inventory" table="t_inventory">
<!-- -->
<id name="itemNo">
<generator class="assigned"/>
</id>
<!-- -->
<property name="itemName"/>
<property name="quantity"/>
</class>
</hibernate-mapping>
테스트 클래스:채산 원 1 비관 적 잠 금 방식 으로 데 이 터 를 불 러 오고 데 이 터 를 수정 합 니 다!
public void testLoad1() {
Session session = null;
try {
session = HibernateUtils.getSession();
session.beginTransaction();
/* , */
Inventory inv = (Inventory) session.load(Inventory.class, "1001", LockMode.UPGRADE);
/* */
System.out.println("opt1-->itemNo=" + inv.getItemNo());
System.out.println("opt1-->itemName=" + inv.getItemName());
System.out.println("opt1-->quantity=" + inv.getQuantity());
/* 200*/
inv.setQuantity(inv.getQuantity() - 200);
session.getTransaction().commit();
} catch (Exception e) {
e.printStackTrace();
session.getTransaction().rollback();
} finally {
HibernateUtils.closeSession(session);
}
}
계산 원 2 와 계산 원 1 의 조작 이 같 고 모두 데이터 베 이 스 를 수정 합 니 다!
public void testLoad2() {
Session session = null;
try {
session = HibernateUtils.getSession();
session.beginTransaction();
/* , */
Inventory inv = (Inventory) session.load(Inventory.class, "1001", LockMode.UPGRADE);
/* */
System.out.println("opt2-->itemNo=" + inv.getItemNo());
System.out.println("opt2-->itemName=" + inv.getItemName());
System.out.println("opt2-->quantity=" + inv.getQuantity());
/* 200*/
inv.setQuantity(inv.getQuantity() - 200);
session.getTransaction().commit();
} catch (Exception e) {
e.printStackTrace();
session.getTransaction().rollback();
} finally {
HibernateUtils.closeSession(session);
}
}
주:두 계산 원 이 하 는 조작 이 같 습 니 다.비관 적 인 자 물 쇠 를 추가 한 후에 계산 원 이 데 이 터 를 꺼 내 데 이 터 를 수정 하면 계산 원 1 이 사물 을 제출 하지 않 기 전에 계산 원 2 는 데 이 터 를 방문 할 수 없고 대기 상태 에 있 을 수 밖 에 없습니다.채산 원 1 이 사물 을 제출 한 것 을 알 고 채산 원 2 는 데이터베이스 에 있 는 데 이 터 를 조작 할 기회 가 있 었 다.위의 비관 적 인 잠 금 사례 를 통 해 알 수 있 듯 이 비관 적 인 잠 금 의 가장 큰 장점 은 업데이트 손실 을 방지 하 는 것 이다.계산 원 1 이 데 이 터 를 처리 할 때 계산 원 2 는 대기 상태 에 있 을 수 밖 에 없고 계산 원 1 이 사물 을 제출 한 후에 야 계산 원 2 가 데 이 터 를 수정 할 수 있다.그러나 큰 문제 도 존재 한다.즉,채산 원 1 이 데 이 터 를 조회 한 후에 가 버 리 면 다른 사람들 은 반나절 을 기 다 려 야 하고 시간 을 낭비 하 는 것 이다.이 문 제 를 해결 하기 위해 우 리 는 낙관적 인 자 물 쇠 를 사용 할 수 있다.
낙관적 자물쇠
낙관적 인 잠 금 은 진정한 의미 의 잠 금 이 아 닙 니 다.대부분의 경우 데이터 버 전(version)방식 으로 이 루어 집 니 다.일반적으로 데이터베이스 에 version 필드 를 추가 하고 데 이 터 를 읽 을 때 version 을 읽 습 니 다.데 이 터 를 저장 할 때 version 의 값 이 데이터베이스 의 version 값 보다 작은 지 판단 합 니 다.작 으 면 업데이트 하지 않 습 니 다.그렇지 않 으 면 업 데 이 트 를 합 니 다.
낙관적 으로 잠 긴 javaBean 설정,Inventory.java:
public class Inventory {
/* */
private String itemNo;
/* */
private String itemName;
/* */
private int quantity;
/* */
private int version;
// setter getter
}
Inventory.hbm.xml:
<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
"http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
<!-- class optimistc-lock , -->
<class name="com.lixue.bean.Inventory" table="t_inventory" optimistic-lock="version">
<!-- -->
<id name="itemNo">
<generator class="assigned"/>
</id>
<!-- , -->
<version name="version"/>
<!-- -->
<property name="itemName"/>
<property name="quantity"/>
</class>
</hibernate-mapping>
주:낙관적 인 잠 금 을 사용 하 는 맵 파일 은 version 필드 의 맵 이 홈 키 ID 이후 에 첫 번 째 로 매 핑 되 어야 한 다 는 규정 이 있 습 니 다.테스트:
채산 원 1 낙관적 인 잠 금 상태 에서 데 이 터 를 처리 합 니 다.
public void testLoad1() {
Session session = null;
try {
session = HibernateUtils.getSession();
session.beginTransaction();
/* */
Inventory inv = (Inventory)session.load(Inventory.class, "1001");
/* */
System.out.println("opt1-->itemNo=" + inv.getItemNo());
System.out.println("opt1-->itemName=" + inv.getItemName());
System.out.println("opt1-->version=" + inv.getVersion());
System.out.println("opt1-->quantity=" + inv.getQuantity());
/* 200*/
inv.setQuantity(inv.getQuantity() - 200);
session.getTransaction().commit();
}catch(Exception e) {
e.printStackTrace();
session.getTransaction().rollback();
}finally {
HibernateUtils.closeSession(session);
}
}
채산 원 2 낙관적 인 잠 금 상태 에서 데 이 터 를 처리 합 니 다(채산 원 2 는 채산 원 1 이 데 이 터 를 제출 하지 않 은 전제 에서 데 이 터 를 처리 할 수 있 습 니 다)
public void testLoad2() {
Session session = null;
try {
session = HibernateUtils.getSession();
session.beginTransaction();
/* */
Inventory inv = (Inventory)session.load(Inventory.class, "1001");
/* */
System.out.println("opt2-->itemNo=" + inv.getItemNo());
System.out.println("opt2-->itemName=" + inv.getItemName());
System.out.println("opt2-->version=" + inv.getVersion());
System.out.println("opt2-->quantity=" + inv.getQuantity());
/* 200*/
inv.setQuantity(inv.getQuantity() - 200);
session.getTransaction().commit();
}catch(Exception e) {
e.printStackTrace();
session.getTransaction().rollback();
}finally {
HibernateUtils.closeSession(session);
}
}
주:채산 원 이 데 이 터 를 꺼 내 200 을 뺀 후에 제출 하지 않 은 전제 에서 채산 원 2 도 데 이 터 를 조작 할 수 있 습 니 다.이것 은 비관 적 인 자물쇠 와 달리 채산 원 2 가 데 이 터 를 조작 하고 제출 한 후에 데이터 베이스 에 데이터 버 전 version 이 1 을 추가 합 니 다.그러면 채산 원 1 이 돌아 와 서 사물 을 제출 할 때 오류 알림 이 발생 합 니 다.즉,데이터 가 업데이트 되 었 으 니 다시 불 러 오 십시오.총결산
비관 적 인 자 물 쇠 는 높 은 병발 에 영향 을 미 치기 때문에 낙관적 인 자 물 쇠 를 사용 하 는 것 이 좋다.
이상 은 바로 본 고 에서 Hibernate 비관 적 인 자물쇠 와 낙관적 인 자물쇠 사례 에 대한 상세 한 설명 의 모든 내용 입 니 다.여러분 에 게 도움 이 되 기 를 바 랍 니 다.관심 이 있 는 친 구 는 본 사이트 의 다른 관련 주 제 를 계속 참고 할 수 있 습 니 다.부족 한 점 이 있 으 면 댓 글로 지적 해 주 십시오.본 사이트 에 대한 여러분 의 지지 에 감 사 드 립 니 다!
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
Is Eclipse IDE dying?In 2014 the Eclipse IDE is the leading development environment for Java with a market share of approximately 65%. but ac...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.