반응형
[Java Class.05] Singleton & final
1.싱글톤(Singleton)
- 싱글톤(Singleton): 단 하나의 객체만 생성하게 만드는 것.
- new 연산자로 생성자를 호출한 만큼 객체가 생성되기 때문에, 단 하나의 객체만 생성하도록 하려면, 클래스 외부에서 new 연산자로 생성자를 호출할 수 없도록 막아야 한다.
- 생성자를 외부에서 호출할 수 없도록 하려면 생성자 앞에 private 접근 제한자를 추가해 주면 된다.
// 싱글톤(Singleton) 방식의 클래스 예제 코드
public class Book {
// 단 하나의 객체 생성
private static Book singleton_book = new Book();
private Book() { } // 생성자(private은 다른 클래스에서 접근X)
static Book getInstance() { // 만들어진 객체 리턴
return singleton_book;
}
}
// 싱글톤 객체(Singleton object)
public class Main {
public static void main(String[] args) {
// Book b1 = new Book(); => error, because of singleton
Book b2 = Book.getInstance();
Book b3 = Book.getInstance();
if(b2 == b3) System.out.println("Same object by singleton.");
else System.out.println("Different obeject.");
}
}
2.final 필드
- final 필드: 필드에 초기값이 저장되면, 이 값이 최종(final)적인 값이 되어서 프로그램 실행 도중에 수정할 수 없다는 것(수정 시도시 에러 발생)
- final 필드의 초기값을 주는 방법은, (1) 필드 선언 시에 주거나, (2) 생성자에서 준다.
- 객체 생성시 초기화 되지 않은 final 필드를 그대로 남겨두면 컴파일 에러가 발생하므로, 생성자에서 final 필드의 최종 초기화를 완료해야 한다.
public class Person {
final String nationality = "Korea"; // 국적(final 필드)
final String nationalID; // 주민번호(final 필드)
String name; // 이름
public Person(String nationalID, String name) {
// 생성자 안에서 final 변수를 초기화
this.nationalID = nationalID;
this.name = name;
}
}
// final 필드 테스트
public class Main {
public static void main(String[] args) {
Person p1 = new Person("123456-1234567", "홍길동");
System.out.println(p1.nationality);
System.out.println(p1.nationalID);
System.out.println(p1.name);
// p1.nationality = "USA"; => error because of final field
// p1.nationalID = "987654-987654"; => error because of final field
p1.name = "김길동"; // OK because of non-final field
}
}
- 위 코드에서 보듯이, final 필드값이 초기화 된 이후에는 수정될 수 없다.
3.상수(constant)
- 처음부터 변하면 안되는 값인 "상수"를 필드에 저장할 때는 static final 을 필드앞에 붙입니다.
- 수학에서 사용되는 원주율 파이나 지구의 무게 등의 상수값을 표현할 때 static final 을 사용합니다.
- 상수의 이름은 모두 대문자로 쓰는게 관례입니다.
static final double PI = 3.14;
static final int EARTH_RADIUS = 6400;
4.final 과 static final의 차이점
- final 필드가 한 번 초기화 되면 수정할 수 없으니 "상수"라고 생각할 수 있겠지만, 그렇지 않습니다.
- final필드는 객체마다 저장되고, 생성자의 매개값을 통해서 여러 가지 값을 가질 수 있기 때문에 "상수"가 될수 없습니다.
- static final 필드는 객체마다 존재하지 않고 클래스에만 존재하므로, 한 번 초기값이 저장되면 변경될 수 없어 "상수"라고 부릅니다.
- 따라서, 자바에서 상수는 static이면서 final이어야 한다.
public class Earth {
static final int EARTH_RADIUS = 6371;
static final double EARTH_SURFACE_AREA;
static { // static block
EARTH_SURFACE_AREA = 4 * Math.PI * EARTH_RADIUS * EARTH_RADIUS;
// Math.PI는 원주율을 반환한다.(자바의 기본제공 함수)
}
}
// 상수(static final) 사용 테스트
public class Main {
public static void main(String[] args) {
System.out.println(Earth.EARTH_RADIUS + "km");
System.out.println(Earth.EARTH_SURFACE_AREA + "km^2");
}
}
- static final(상수)의 초기값이 단순하다면 선언 시에 주는 것이 일반적이다.
- 만약 초기값이 복잡하다면 static block을 사용해 초기값을 줄 수도 있다.
728x90
반응형
'자바(Java) > 자바 클래스' 카테고리의 다른 글
[Java Class.07] 다형성(Polymorphism) (0) | 2024.02.23 |
---|---|
[Java Class.06] 상속(Inheritance) (0) | 2024.02.23 |
[Java Class.04] Member of Instance & Static (0) | 2024.02.23 |
[Java Class.03] 메소드(Method) (0) | 2024.02.18 |
[Java Class.02]필드, 생성자 (0) | 2024.02.18 |
댓글