프로젝트에서 PMD 정적 코드 감지를 수행할 때 이러한 문제가 발생했습니다.
Java에서 사용할 때 부분적으로 생성된 객체가 Double Checked Locking 패턴에 의해 반환될 수 있습니다. 최적화 JRE는 baz 변수에 대한 참조를 할당할 수 있습니다. 참조가 가리키는 개체의 생성자를 호출하기 전에.
참고: Java 5에서는 변수를 휘발성으로 선언하면 이중 확인 잠금이 작동하도록 할 수 있습니다.
아마도 이중 확인 잠금 모드를 사용할 때 불완전하게 초기화된 객체를 반환합니다. 일부 사람들은 부분적으로 초기화된 객체의 개념을 의심할 수 있습니다. 계속 분석해 보세요.
<code>public static Singleton getSingleton() {<br> if (instance == null) { <br> synchronized (Singleton.class) {<br> if (instance == null) { <br> instance = new Singleton();<br> }<br> }<br> }<br> return instance ;<br>}</code>
instance == null이 동기화된 코드 블록 내부와 외부 모두에서 판단되는 것을 볼 수 있습니다. 스레드는 동시에 동기화된 코드 블록 외부에서 if 판단을 입력할 수 있습니다. 동기화된 코드 블록 내부에서 null 판단이 수행되지 않으면 여러 인스턴스가 초기화될 수 있습니다.
이런 글쓰기 방식은 완벽해 보이지만 문제가 있거나 완벽하다는 보장은 없습니다. 주된 이유는 instance = new Singleton();이 원자적 연산이 아니기 때문입니다.
객체 생성은 세 부분으로 나눌 수 있습니다:
<code>1.分配对象的内存空间<br>2.初始化对象<br>3.设置instance指向刚分配的内存地址<br>当instance指向分配地址时,instance是不为null的</code>
그러나 2단계와 3단계 사이에서 순서가 바뀌어 객체 생성 순서가 1-3-2가 될 수 있습니다.
스레드 A는 다음과 같습니다. 처음에는 Singleton 객체를 생성하며, 객체 생성 순서는
인스턴스에 메모리를 할당한 후 스레드 B가 와서 getSingleton() 메서드를 호출합니다. 이때 해당 인스턴스라고 판단합니다. == null이며 인스턴스가 Not null이 아닌 것으로 확인되었습니다.
그러나 현재 인스턴스는 개체를 초기화하지 않았으며 스레드 B는 초기화되지 않은 개체를 반환합니다. Thread B가 인스턴스를 사용할 때 문제가 발생할 수 있습니다. 이것이 Double-Check Lock의 문제입니다.
<code>public class Singleton{<br> private volatile static Singleton instance;<br> public static Singleton getSingleton() {<br> if (instance == null) { <br> synchronized (Singleton.class) {<br> if (instance == null) { <br> instance = new Singleton();<br> }<br> }<br> }<br> return instance ;<br> }<br>}</code>단, JDK5 버전 이상에서는 사용해야 합니다. 정적 내부 클래스
<code>public class Singleton { <br> private static class SingletonHolder { <br> private static final Singleton INSTANCE = new Singleton(); <br> } <br> private Singleton (){} <br> public static final Singleton getInstance() { <br> return SingletonHolder.INSTANCE; <br> } <br>}</code>
위 내용은 Java 이중 확인 잠금 모드란 무엇입니까?의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!