1 ~ 9
์์ดํ
1. ์์ฑ์ ๋์ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ ๊ณ ๋ คํ๋ผ
ยท ํด๋์ค์ ์ธ์คํด์ค๋ฅผ ์ป๊ธฐ ์ํด ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋(static factory method)๋ฅผ ์ ๊ณตํ ์ ์๋ค.
- ์ ํต์ ์ธ ์๋จ: public ์์ฑ์
- ๋์์ธ ํจํด(Gamma95)์ ํฉํฐ๋ฆฌ ๋ฉ์๋์๋ ๋ค๋ฅด๋ค. ์ด์ ์ผ์นํ๋ ํจํด์ ์๋ค.
์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋์ ์ฅ์
1. ์ด๋ฆ์ ๊ฐ์ง ์ ์๋ค.
- ์์ฑ์์ ๋๊ธฐ๋ ๋งค๊ฐ๋ณ์์ ์์ฑ์ ์์ฒด ๋ง์ผ๋ก๋ ๋ฐํ๋ ๊ฐ์ฒด์ ํน์ฑ์ ์ ๋๋ก ์ค๋ช ํ์ง ๋ชปํ๋ค. ๋ฐ๋ฉด ์ ์ ํฉํฐ๋ฆฌ๋ ๋ฐํ๋ ๊ฐ์ฒด์ ํน์ฑ์ ์ฝ๊ฒ ๋ฌ์ฌํ ์ ์๋ค. ex) ๊ฐ์ด ์์์ธ Integer๋ฅผ ๋ฐํํ๋ BigInteger.probablePrime
- ์ฌ๋ฌ ๊ฐ์ ์์ฑ์๊ฐ ์์ ๋, ์๋ฑํ ์์ฑ์๋ฅผ ํธ์ถํ๋ ์ค์๋ฅผ ๋ฐฉ์งํ ์ ์๋ค.
- ํด๋์ค ์ค๋ช ๋ฌธ์๋ฅผ ์ฐพ์๋ณด์ง ์๊ณ ๋ ์๋ฏธ๋ฅผ ์ ์ถํ ์ ์๋ค.
2. ํธ์ถ๋ ๋๋ง๋ค ์ธ์คํด์ค๋ฅผ ์๋ก ์์ฑํ์ง ์์๋ ๋๋ค.
- ์ด๋ฅผ ์ด์ฉํ์ฌ ๋ถ๋ณ ํด๋์ค(immutable class ์์ดํ 17)๋ ์ธ์คํด์ค๋ฅผ ๋ฏธ๋ฆฌ ๋ง๋ค์ด ๋๊ฑฐ๋, ์๋ก ์์ฑํ ์ธ์คํด์ค๋ฅผ ์บ์ฑํ์ฌ ์ฌํ์ฉํ๋ ๋ฐฉ์์ผ๋ก ๋ถํ์ํ ๊ฐ์ฒด ์์ฑ์ ํผํ ์ ์๋ค.
- ์์ฑ๋น์ฉ์ด ํฌ๊ณ , ์์ฃผ ์์ฒญ๋๋ ๊ฐ์ฒด๋ผ๋ฉด ์ฑ๋ฅ์ ์๋นํ ๋์ด์ฌ๋ฆด ์ ์๋ค. ํ๋ผ์ด์จ์ดํธ ํจํด[Gamma97]๋ ์ด์ ๋น์ทํ ๊ธฐ๋ฒ์ด๋ค.
- ๋ฐ๋ณต๋๋ ์์ฒญ์ ๊ฐ์ ๊ฐ์ฒด๋ฅผ ๋ฐํํ๋ ์์ผ๋ก ์ด๋ ์ธ์คํด์ค๋ฅผ ์ด์ ์๊ฒ ํ ์ง ์ฒ ์ ํ ํต์ ํ ์ ์๋ค. ์ธ์คํด์ค ํต์ ๋ ํ๋ผ์ด์จ์ดํธ ํจํด์ ๊ทผ๊ฐ์ด ๋๋ฉฐ, ์ด๊ฑฐ ํ์ ์ ์ธ์คํด์ค๊ฐ ํ๋๋ง ๋ง๋ค์ด์ง์ ๋ณด์ฅํ๋ค.
์ธ์คํด์ค ํต์ ์ด์ โ
๋๋ณด๊ธฐ
TODO: ํ๋ผ์ด์จ์ดํธํจํด
3. ๋ฐํ ํ์ ์ ํ์ ํ์ ๊ฐ์ฒด๋ฅผ ๋ฐํํ ์ ์๋ค.
- ๋ฐํํ ๊ฐ์ฒด์ ํด๋์ค๋ฅผ ์์ ๋กญ๊ฒ ์ ํํ ์ ์๋ ์ ์ฐ์ฑ์ ์ ๊ณตํ๋ค.
- ์ ์ฐ์ฑ์ ์์ฉํ์ฌ ๊ตฌํ ํด๋์ค๋ฅผ ๊ณต๊ฐํ์ง ์๊ณ ๋ ๊ทธ ๊ฐ์ฒด๋ฅผ ๋ฐํํ ์ ์์ด API๋ฅผ ์๊ฒ ์ ์งํ ์ ์๋ค.
- ์ธํฐํ์ด์ค๋ฅผ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋์ ๋ฐํ ํ์ ์ผ๋ก ์ฌ์ฉํ๋ ์ธํฐํ์ด์ค ๊ธฐ๋ฐ ํ๋ ์์ํฌ(์์ดํ 20)๋ฅผ ๋ง๋๋ ํต์ฌ ๊ธฐ์ ์ด๊ธฐ๋ ํ๋ค.
๋๋ณด๊ธฐ
4. ์ ๋ ฅ ๋งค๊ฐ๋ณ์์ ๋ฐ๋ผ ๋งค๋ฒ ๋ค๋ฅธ ๊ฐ์ฒด๋ฅผ ๋ฐํํ ์ ์๋ค.
- ํด๋ผ์ด์ธํธ๋ฅผ ๋ฐํ๋๋ ๊ฐ์ฒด๋ค์ ์กด์ฌ๋ฅผ ๋ชจ๋ฅธ๋ค. ๋ฐ๋ผ์ ๋ค์ ๋ฒ์ ์์ ์ํ๋๋๋ก ์์ ํ ์ ์์ผ๋ฏ๋ก, ์ ์ง๋ณด์๊ฐ ํธ๋ฆฌํ๋ค.
ex) EnumSet ํด๋์ค๋ Public ์์ฑ์ ์์ด ์ ์ ํฉํฐ๋ฆฌ๋ง ์ ๊ณตํ๋ฉฐ, ์์๊ฐ 64๊ฐ ์ดํ๋ฉด long ๋ณ์ ํ๋๋ก ๊ด๋ฆฌํ๋ RegularEnumSet์ ์ธ์คํด์ค๋ฅผ, 65๊ฐ ์ด์์ด๋ฉด long ๋ฐฐ์ด๋ก ๊ด๋ฆฌํ๋ JumboEnumSet์ ์ธ์คํด์ค๋ฅผ ๋ฐํํ๋ค. (OpenJDK๊ธฐ์ค)
5. ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ ์์ฑํ๋ ์์ ์ ๋ฐํํ ๊ฐ์ฒด์ ํด๋์ค๊ฐ ์กด์ฌํ์ง ์์๋ ๋๋ค.
- ์ด๋ฐ ์ ์ฐํจ์ ์๋น์ค ์ ๊ณต์ ํ๋ ์์ํฌ๋ฅผ ๋ง๋๋ ๊ทผ๊ฐ์ด ๋๋ค. ex)JDBC
- ์ ๊ณต์(provider): ์๋น์ค์ ๊ตฌํ์ฒด๋ก ํด๋ผ์ด์ธํธ์์ ์ ๊ณตํ๋ ์ญํ ์ ํ๋ ์์ํฌ๊ฐ ํต์ ํ์ฌ, ํด๋ผ์ด์ธํธ์ ๊ตฌํ์ฒด๋ก๋ถํฐ ๋ถ๋ฆฌํด์ค๋ค.
์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋์ ๋จ์
1. ์์์ ํ๋ ค๋ฉด public์ด๋ protected ์์ฑ์๊ฐ ํ์ํ๋ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ง ์ ๊ณตํ๋ฉด ํ์ ํด๋์ค๋ฅผ ๋ง๋ค ์ ์๋ค.
- ์์๋ณด๋ค ์ปดํฌ์ง์ ์ ์ฌ์ฉ(์์ดํ 18)ํ๋๋ก ์ ๋ํ๊ณ , ๋ถ๋ณ ํ์ ์ผ๋ก ๋ง๋ค๋ ค๋ฉด ์ด ์ ์ฝ์ ์ง์ผ์ผ ํ๋ค๋ ์ ์์ ์คํ๋ ค ์ฅ์ ์ผ๋ก ๋ฐ์๋ค์ผ ์๋ ์๋ค.
2. ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ ํ๋ก๊ทธ๋๋จธ๊ฐ ์ฐพ๊ธฐ ์ด๋ ต๋ค.
- ์์ฑ์์ฒ๋ผ API ์ค๋ช ์ ๋ช ํํ ๋๋ฌ๋์ง ์์ผ๋ฏ๋ก, ์ฌ์ฉ์๋ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋ ๋ฐฉ์ ํด๋์ค๋ฅผ ์ธ์คํด์คํํ ๋ฐฉ๋ฒ์ ์์๋ด์ผ ํ๋ค.
- API ๋ฌธ์๋ฅผ ์ ์จ๋๊ณ , ๋ฉ์๋ ์ด๋ฆ๋ ๋๋ฆฌ ์๋ ค์ง ๊ท์ฝ์ ๋ฐ๋ผ ์ง๋ ์์ผ๋ก ๋ฌธ์ ๋ฅผ ์ํํ์.


์์ฃผ ์ฌ์ฉํ๋ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋ ๋ช ๋ช ๋ฐฉ์
ยท from - ๋งค๊ฐ๋ณ์๋ฅผ ํ๋๋ง ๋ฐ์์ ํด๋น ํ์ ์ ์ธ์คํด์ค๋ฅผ ๋ฐํํ๋ ๋ฉ์๋
์์) Date date = Date.from(dateStr);
ยท of - ์ฌ๋ฌ ๋งค๊ฐ๋ณ์๋ฅผ ๋ฐ์ ์ ํฉํ ํ์ ์ ์ธ์คํด์ค๋ฅผ ๋ฐํํ๋ ์ง๊ณ ๋ฉ์๋
์์) Set<Rank> faceCards = EnumSet.of(JACK, QUEEN, KING);
ยท valueOf - from๊ณผ of์ ๋ ์์ธํ ๋ฒ์
์์) BigInteger prime = BigInteger.valueOf(Integer.MAX_VALUE);
ยท instance(getInstance) - ๋งค๊ฐ๋ณ์๋ฅผ ๋ฐ๋๋ค๋ฉด, ๋งค๊ฐ๋ณ์๋ก ๋ช ์ํ ์ธ์คํด์ค๋ฅผ ๋ฐํํ์ง๋ง, ๊ฐ์ ์ธ์คํด์ค์์ ๋ณด์ฅํ์ง ์๋๋ค. ์ฑ๊ธํด์ผ ์๋ ์๋ค.
์์) StackWalker luke = StackWalker.getInstance(options);
ยท create(newInstance) - instance/getInstance์ ๊ฐ์ง๋ง, ๋งค๋ฒ ์๋ก์ด ์ธ์คํด์ค๋ฅผ ๋ฐํํจ์ ๋ณด์ฅํ๋ค.
ยท getType - getInstance์ ๋งฅ๋ฝ์ ๊ฐ์ผ๋ ํน์ Type์ ๋ฐํํ ๋ ์ฌ์ฉ
์์) Steak steak = Food.getSteak(Meet.BEEF);
ยท newType - newInstance์ ๊ฐ์ผ๋, ์์ฑํ ํด๋์ค๊ฐ ์๋ ๋ค๋ฅธ ํด๋์ค์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ ์ ์ ํ ๋ ์ฌ์ฉ
์์) Steak steak = Food.newSteak(Meet.BEEF);
ยท Type - getType, newType์ ๊ฐ๊ฒฐํ ๋ฒ์
์์) Steak steak = Food.steak(Meet.BEEF);
์์ดํ
2. ์์ฑ์์ ๋งค๊ฐ๋ณ์๊ฐ ๋ง๋ค๋ฉด ๋น๋๋ฅผ ๊ณ ๋ คํ๋ผ
ยท ์ ์ ํฉํฐ๋ฆฌ์ ์์ฑ์๋ ์ ํ์ ๋งค๊ฐ๋ณ์๊ฐ ๋ง์ ๋ ์ ์ ํ ๋์ํ๊ธฐ ์ด๋ ต๋ค๋ ์ ์ฝ์ด ์๋ค.
ยท ์ด๋ฌํ ๋ฌธ์ ์ ๋์์ผ๋ก ์ ์ธต์ ์์ฑ์ ํจํด(telescoping constructor pattern)๊ณผ ์๋ฐ๋น์ฆ ํจํด์ด ๋ฑ์ฅํ์ง๋ง, ํ๊ณ๊ฐ ์กด์ฌํ๋ค.
๋๋ณด๊ธฐ
ยท ์ ์ธต์ ์์ฑ์ ํจํด์ ์์ ์ฑ๊ณผ ์๋ฐ๋น์ฆ ํจํด์ ๊ฐ๋ ์ฑ์ ๊ฒธ๋นํ ๋น๋ ํจํด์ผ๋ก ์ด๋ฌํ ๋ฌธ์ ๋ฅผ ํด๊ฒฐํ ์ ์๋ค.
- ํด๋ผ์ด์ธํธ๋ ํ์ํ ๊ฐ์ฒด๋ฅผ ์ง์ ๋ง๋๋ ๋์ , ํ์ ๋งค๊ฐ๋ณ์๋ง์ผ๋ก ์์ฑ์๋ ์ ์ ํฉํฐ๋ฆฌ๋ฅผ ํธ์ถํด ๋น๋ ๊ฐ์ฒด๋ฅผ ์ป๊ณ , ๋น๋ ๊ฐ์ฒด๊ฐ ์ ๊ณตํ๋ ์ธํฐ ๋ฉ์๋๋ค๋ก ์ํ๋ ์ ํ ๋งค๊ฐ๋ณ์๋ฅผ ์ค์ ํ๊ณ , ๋งค๊ฐ๋ณ์๊ฐ ์๋ build ๋ฉ์๋๋ฅผ ํธ์ถํด ๊ฐ์ฒด๋ฅผ ์ป๋๋ค.
๋น๋ ํจํด ์์
class NutritionFacts{
private final int servingSize;
private final int servings;
private final int calories;
private final int fat;
private final int sodium;
private final int carbohydrate;
public static class Builder{
// ํ์ ๋งค๊ฐ๋ณ์
private final int servingSize;
private final int servings;
// ์ ํ ๋งค๊ฐ๋ณ์
private int calories = 0;
private int fat = 0;
private int sodium = 0;
private int carbohydrate = 0;
public Builder(int servingSize, int servings) {
this.servingSize = servingSize;
this.servings = servings;
}
public Builder calories(int calories){
this.calories = calories;
return this;
}
public Builder fat(int fat){
this.fat = fat;
return this;
}
public Builder sodium(int sodium){
this.sodium = sodium;
return this;
}
public Builder carbohydrate(int carbohydrate){
this.carbohydrate = carbohydrate;
return this;
}
public NutritionFacts build(){
return new NutritionFacts(this);
}
}
private NutritionFacts(Builder builder){
servingSize = builder.servingSize;
servings = builder.servings;
calories = builder.calories;
fat = builder.fat;
sodium = builder.sodium;
carbohydrate = builder.carbohydrate;
}
}
๋น๋ ํจํด ์ฌ์ฉ๋ฒ
ยท ์ด ํด๋ผ์ด์ธํธ ์ฝ๋๋ ์ฐ๊ธฐ ์ฝ๊ณ ์ฝ๊ธฐ ์ฝ๋ค.
NutritionFacts cocaCola = new NutritionFacts.Builder(240, 8)
.calories(100)
.sodium(35)
.carbohydrate(27).build();
ยท ๋น๋ ํจํด์ ํ์ด์ฌ๊ณผ ์ค์นผ๋ผ์ ์๋ ๋ช ๋ช ๋ ์ ํ์ ๋งค๊ฐ๋ณ์(named optional parameters)๋ฅผ ํ๋ด ๋ธ ๊ฒ์ด๋ค.
ยท ๋น๋์ ์ธํฐ ๋ฉ์๋๋ค์ ๋น๋ ์์ ์ ๋ฐํํ๊ธฐ ๋๋ฌธ์ ์ฐ์์ ์ผ๋ก ํธ์ถํ ์ ์๋ค. ์ด๋ฌํ ๋ฐฉ์์ ๋ฉ์๋ ํธ์ถ์ด ํ๋ฅด๋ฏ ์ฐ๊ฒฐ๋๋ค๋ ๋ป์ผ๋ก ํ๋ฃจ์ธํธ API ํน์ ๋ฉ์๋ ์ฐ์๋ผ ํ๋ค.
ยท ์๋ชป๋ ๋งค๊ฐ๋ณ์๋ฅผ ์ผ์ฐ ๋ฐ๊ฒฌํ๊ธฐ์ํด ๋น๋์ ์์ฑ์์ ๋ฉ์๋์์ ์ ๋ ฅ ๋งค๊ฐ๋ณ์๋ฅผ ๊ฒ์ฌํ๊ณ , build ๋ฉ์๋๊ฐ ํธ์ถํ๋ ์์ฑ์์์ ์ฌ๋ฌ ๋งค๊ฐ๋ณ์์ ๊ฑธ์น ๋ถ๋ณ์์ ๊ฒ์ฌํ์.
- ๋ถ๋ณ(immutable ํน์ immutability): ์ด๋ ํ ๋ณ๊ฒฝ๋ ํ์ฉํ์ง ์๋๋ค๋ ๋ป์ผ๋ก ๋ณ๊ฒฝ์ ํ์ฉํ๋ ๊ฐ๋ณ(mutable) ๊ฐ์ฒด์ ๊ตฌ๋ถํ๋ ์ฉ๋๋ก ์ฐ์ธ๋ค.
ยท ๋น๋ ํจํด์ ๊ณ์ธต์ ์ผ๋ก ์ค๊ณ๋ ํด๋์ค์ ํจ๊ป ์ฐ๊ธฐ์ ์ข๋ค.
public abstract class Pizza{
public enum Topping { HAM, MUSHROOM, ONION, PEPPER, SAUSAGE }
final Set<Topping> toppings;
abstract static class Builder<T extends Builder<T>>{
EnumSet<Topping> toppings = EnumSet.noneOf(Topping.class);
public T addTopping(Topping topping){
toppings.add(Objects.requireNonNull(topping));
return self();
}
abstract Pizza build();
protected abstract T self();
}
Pizza(Builder<?> builder){
toppings = builder.toppings.clone();
}
}
public class NyPizza extends Pizza{
public enum Size { SMALL, MEDIUM, LARGE }
private final Size size;
public static class Builder extends Pizza.Builder<Builder>{
private final Size size;
public Builder(Size size){
this.size = Objects.requireNonNull(size);
}
@Override public NyPizza build(){
return new NyPizza(this);
}
@Override protected Builder self(){
return this;
}
}
private NyPizza(Builder builder){
super(builder);
size = builder.size();
}
}
public class Calzone extends Pizza{
private final boolean sauceInside;
public static class Builder extends Pizza.Builder<Builder>{
private boolean sauceInside = false;
public Builder sauceInside(){
sauceInside = true;
return this;
}
@Override public Calzone builde(){
return new Calzone(this);
}
@Override protected Builder self(){ return this; }
}
private Calzone(Builder builder){
super(builder);
sauceInside = builder.sauceInside;
}
}
// ๊ฐ์ฒด ์์ฑ
NyPizza pizza = new NyPizza.Builder(SMALL)
.addTopping(SAUSAGE).addTopping(ONION).build();
Calzone calzone = new Calzone.Builder()
.addTopping(HAM).sauceInside().build();
ยท Pizza.Builder ํด๋์ค๋ ์ฌ๊ท์ ํ์ ํ์ ์ ์ด์ฉํ๋ ์ ๋ค๋ฆญ ํ์ ์ด๋ค. ์ฌ๊ธฐ์ ์ถ์ ๋ฉ์๋์ธ self๋ฅผ ๋ํด ํ์ ํด๋์ค์์ ํ๋ณํํ์ง ์๊ณ ๋ ๋ฉ์๋ ์ฐ์๋ฅผ ์ง์ํ ์ ์๋ค.
ยท ๊ฐ ํ์ ํด๋์ค์ ๋น๋๊ฐ ์ ์ํ build ๋ฉ์๋๋ ํด๋นํ๋ ๊ตฌ์ฒด ํ์ ํด๋์ค๋ฅผ ๋ฐํํ๋ค. ํ์ ํด๋์ค์ ๋ฉ์๋๊ฐ ์์ ํด๋์ค์ ๋ฉ์๋๊ฐ ์ ์ํ ๋ฐํ ํ์ ์ด ์๋, ๊ทธ ํ์ ํ์ ์ ๋ฐํํ๋ ๊ธฐ๋ฅ์ ๊ณต๋ณ๋ฐํ ํ์ดํ(covariant return typing)์ด๋ผ ํ๋ค. ์ด ๊ธฐ๋ฅ์ ์ด์ฉํ๋ฉด ํด๋ผ์ด์ธํธ๊ฐ ํ๋ณํ์ ์ ๊ฒฝ ์ฐ์ง ์๊ณ ๋น๋๋ฅผ ์ฌ์ฉํ ์ ์๋ค.
ยท ๋น๋ ํจํด์ ์ ์ฐํ๋ค. ๋น๋ ํ๋๋ก ์ฌ๋ฌ ๊ฐ์ฒด๋ฅผ ์ํํ๋ฉด์ ๋ง๋ค ์ ์๊ณ , ๋น๋์ ๋๊ธฐ๋ ๋งค๊ฐ๋ณ์์ ๋ฐ๋ผ ๋ค๋ฅธ ๊ฐ์ฒด๋ฅผ ๋ง๋ค ์๋ ์๊ณ , ๊ฐ์ฒด๋ง๋ค ๋ถ์ฌ๋๋ ์ผ๋ จ๋ฒํธ์ ๊ฐ์ ํน์ ํ๋๋ ๋น๋๊ฐ ์์์ ์ฑ์ฐ๋๋ก ํ ์๋ ์๋ค.
๋จ์
ยท ๋น๋ ์์ฑ ๋น์ฉ์ด ํฌ์ง๋ ์์ง๋ง ์ฑ๋ฅ์ ๋ฏผ๊ฐํ ์ํฉ์์๋ ๋ฌธ์ ๊ฐ ๋ ์ ์๋ค.
ยท ์ฝ๋๊ฐ ์ฅํฉํ๋ค.
+ ์ถ๊ฐ์ ์ธ ๋ฐฉ๋ฒ
1. ํ๋ ๊ฐ๋ง ๋ค์ด์๋ ํด๋์ค๋ฅผ ๋ง๋ค์ด DIํ๋ค.
2. Map ๊ฐ์ ํด๋์ค ํ๋๋ก๋ก ์ฎ๊ธด๋ค.
์์ดํ
3. private ์์ฑ์๋ ์ด๊ฑฐ ํ์
์ผ๋ก ์ฑ๊ธํด์ ๋ณด์ฆํ๋ผ
ยท ์ฑ๊ธํด์ด๋ ์ธ์คํด์ค๋ฅผ ์ค์ง ํ๋๋ง ์์ฑํ ์ ์๋ ํด๋์ค๋ฅผ ๋งํ๋ค.
ex) ํจ์์ ๊ฐ์ ๋ฌด์ํ ๊ฐ์ฒด, ์ค๊ณ์ ์ ์ผํด์ผ ํ๋ ์์คํ ์ปดํฌ๋ํธ
์ฑ๊ธํด์ ๋ฌธ์ ์
ยท ํด๋์ค๋ฅผ ์ฑ๊ธํด์ผ๋ก ๋ง๋ค๋ฉด ์ด๋ฅผ ์ฌ์ฉํ๋ ํด๋ผ์ด์ธํธ๋ฅผ ํ ์คํธํ๊ธฐ ์ด๋ ค์ ์ง ์ ์๋ค.
- ํ์ ์ ์ธํฐํ์ด์ค๋ก ์ ์ํ ํ ๊ทธ ์ธํฐํ์ด์ค๋ฅผ ๊ตฌํํด์ ๋ง๋ ์ฑ๊ธํด์ด ์๋๋ผ๋ฉด ์ฑ๊ธํด ์ธ์คํด์ค๋ฅผ mock ๊ตฌํ์ผ๋ก ๋์ฒดํ ์ ์๊ธฐ ๋๋ฌธ์ด๋ค.
์ฑ๊ธํด์ ๋ง๋๋ ๋ฐฉ์
1. public static ๋ฉค๋ฒ๊ฐ final ํ๋์ธ ๋ฐฉ์
public class Elvis {
public static final Elvis INSTANCE = new Elvis();
private Elvis { ... }
public void leaveTheBuilding() { ... }
}
ยท ์ฅ์ : ํด๋น ํด๋์ค๊ฐ ์ฑ๊ธํด์์ด API์ ๋ช ๋ฐฑํ ๋๋ฌ๋๋ค. public static ํ๋๊ฐ final์ด๋ ์ ๋๋ก ๋ค๋ฅธ ๊ฐ์ฒด๋ฅผ ์ฐธ์กฐํ ์ ์๋ค.
ยท ๋ฌธ์ ์ :
1. ๊ถํ์ด ์๋ ํด๋ผ์ด์ธํธ์์ ๋ฆฌํ๋ ์ API์ธ AccessibleObject.setAccessible์ ์ฌ์ฉํด private ์์ฑ์๋ฅผ ํธ์ถ ํ ์ ์๋ค.
2. ์์ฑ๋๋ ์์ ์ ์กฐ์ ํ ์ ์๋ค. (ํด๋์ค๊ฐ ๋ค๋ฅธ ์์(DB์ปค๋ฅ์ ๋ฑ)์ ์์กดํด์ผ ํ๋ค๋ฉด ์ด์ฉ ๋ถ๊ฐ๋ฅ)
- ๋ฐฉ์ด ๋ฐฉ๋ฒ: ์์ฑ์๋ฅผ ์์ ํ์ฌ ๋ ๋ฒ์งธ ๊ฐ์ฒด๊ฐ ์์ฑ๋๋ ค ํ ๋ ์์ธ๋ฅผ ๋์ง๋ค.
2. ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ public static ๋ฉค๋ฒ๋ก ์ ๊ณตํ๋ ๋ฐฉ์
public class Elvis {
private static final Elvis INSTANCE = new Elvis();
private Elvis { ... }
public static Elvis getInstance() {return INSTANCE;}
public void leaveTheBuilding() { ... }
}
ยท ์ฅ์ :
1. API๋ฅผ ๋ฐ๊พธ์ง ์๊ณ ๋ ์ฑ๊ธํด์ด ์๋๊ฒ ๋ณ๊ผํ ์ ์๋ค.
ex) ์ ์ผํ ์ธ์คํด์ค๋ฅผ ๋ฐํํ๋ ํฉํฐ๋ฆฌ ๋ฉ์๋๊ฐ ํธ์ถํ๋ ์ค๋ ๋๋ณ๋ก ๋ค๋ฅธ ์ธ์คํด์ค๋ฅผ ๋๊ฒจ์ค ์ ์๋ค.
2. ์ ์ ํฉํฐ๋ฆฌ๋ฅผ ์ ๋ค๋ฆญ ์ฑ๊ธํด ํฉํฐ๋ฆฌ๋ก ๋ง๋ค ์ ์๋ค. (์์ดํ 30)
3.์ ์ ํฉํฐ๋ฆฌ์ ๋ฉ์๋ ์ฐธ์กฐ๋ฅผ ๊ณต๊ธ์(supplier)๋ก ์ฌ์ฉํ ์ ์๋ค.
ex) Elvis::getInstance๋ฅผ Supplier<Elvis>๋ก ์ฌ์ฉํ ์ ์๋ค. (์์ดํ 43, 44)
ยท ๋ฌธ์ ์ : ๋ฆฌํ๋ ์ ์ ํตํ ์์ธ๋ ๋๊ฐ์ด ์ ์ฉ๋๋ค.
ยท ๋ ๋ฐฉ์ ๋ชจ๋ ์์ฑ์๋ private๋ก ๊ฐ์ถ๊ณ , ์ ์ผํ ์ธ์คํด์ค์ ์ ๊ทผํ ์ ์๋ ์๋จ์ผ๋ก public static ๋ฉค๋ฒ๋ฅผ ํ๋ ๋ง๋ จํ๋ค.
ยท ๋ ์ค ํ๋์ ๋ฐฉ์์ผ๋ก ๋ง๋ ์ฑ๊ธํด ํด๋์ค๋ฅผ ์ง๋ ฌํํ๋ ค๋ฉด, Serializable์ ๊ตฌํํ๋ค๊ณ ์ ์ธํ๋ ๊ฒ๋ง์ผ๋ก๋ ๋ถ์กฑ ํ๋ค.
- ๋ชจ๋ ์ธ์คํด์ค ํ๋๋ฅผ transient๋ก ์ ์ธํ๊ณ , readResolve ๋ฉ์๋๋ฅผ ์ ๊ณตํด์ผ ํ๋ค. (์์ดํ 89)
- ์ด๋ ๊ฒ ํ์ง ์์ผ๋ฉด, ์ง๋ ฌํ๋ ์ธ์คํด์ค๋ฅผ ์ญ์ง๋ ฌํํ ๋๋ง๋ค ์๋ก์ด ์ธ์คํด์ค๊ฐ ๋ง๋ค์ด ์ง๋ค.
// ์ฑ๊ธํด์์ ๋ณด์ฅํด์ฃผ๋ readResolve ๋ฉ์๋
private Object readResolve() {
// '์ง์ง' Elvis๋ฅผ ๋ฐํํ๊ณ , ๊ฐ์ง Elvis๋ ๊ฐ๋น์ง ์ปฌ๋ ํฐ์ ๋งก๋ค.
return INSTANCE;
}
3. ์์๊ฐ ํ๋์ธ ์ด๊ฑฐ ํ์ ์ ์ ์ธํ๋ค.
public enum Elvis {
INSTANCE;
public void leaveTheBuilding() { ... }
}
ยท ์ฅ์ :
1. ๊ฐ๊ฒฐํ๋ค.
2. ์ถ๊ฐ ๋ ธ๋ ฅ ์์ด ์ง๋ ฌํํ ์ ์๋ค.
3. ์์ฃผ ๋ณต์กํ ์ง๋ ฌํ ์ํฉ์ด๋ ๋ฆฌํ๋ ์ ๊ณต๊ฒฉ์๋ ์ 2์ ์ธ์คํด์ค๊ฐ ์๊ธฐ๋ ์ผ์ ์๋ฒฝํ ๋ง์์ค๋ค.
ยท ๋๋ถ๋ถ์ ์ํฉ์์ ์ฑ๊ธํด์ ๋ง๋๋ ๊ฐ์ฅ ์ข์ ๋ฐฉ๋ฒ์ด๋ค.
ยท ๋ฌธ์ ์ : ์ฑ๊ธํด์ด Enum ์ธ์ ํด๋์ค๋ฅผ ์์ํด์ผ ํ๋ค๋ฉด, ์ด ๋ฐฉ๋ฒ์ ์ฌ์ฉํ ์ ์๋ค.
- ์ด๊ฑฐ ํ์ ์ด ๋ค๋ฅธ ์ธํฐํ์ด์ค๋ฅผ ๊ตฌํํ๋๋ก ์ ์ธํ ์ ์๋ค.
์์ดํ
4. ์ธ์คํด์ค๋ฅผ ๋ง์ผ๋ ค๊ฑฐ๋ private ์์ฑ์๋ฅผ ์ฌ์ฉํ๋ผ
ยท ์ ์ ๋ฉ์๋์ ์ ์ ํ๋๋ง ๋ด์ ํด๋์ค๋ ๊ฐ์ฒด ์งํฅ์ ์ผ๋ก ์ฌ๊ณ ํ์ง ์๋ ์ฌ๋๋ค์ด ์ข ์ข ๋จ์ฉํ๋ ๋ฐฉ์์ด์ง๋ง, ๋๋ฆ์ ์ฐ์์๊ฐ ์๋ค.
1. java.lang.Math, java.util.Arrays์ฒ๋ผ ๊ธฐ๋ณธ ํ์ ๊ฐ์ด๋ ๋ฐฐ์ด ๊ด๋ จ ๋ฉ์๋๋ค์ ๋ชจ์๋์ ์ ์๋ค.
2. java.util.Collections์ฒ๋ผ ํน์ ์ธํฐํ์ด์ค๋ฅผ ๊ตฌํํ๋ ๊ฐ์ฒด๋ฅผ ์์ฑํด์ฃผ๋ ์ ์ ๋ฉ์๋(ํน์ ํฉํฐ๋ฆฌ)๋ฅผ ๋ชจ์๋์ ์ ์๋ค.
(์๋ฐ 8 ๋ถํฐ๋ ์ด๋ฐ ๋ฉ์๋๋ฅผ ์ธํฐํ์ด์ค์ ๋ฃ์ ์ ์๋ค)
3. final ํด๋์ค์ ๊ด๋ จ๋ ๋ฉ์๋๋ฅผ ๋ชจ์ ๋์ ๋ ์ฌ์ฉํ๋ค. final ํด๋์ค๋ฅผ ์์ํด์ ํ์ ํด๋์ค์ ๋ฉ์๋๋ฅผ ๋ฃ๋ ๊ฑด ๋ถ๊ฐ๊ธฐ ๋๋ฌธ์ด๋ค.
ยท ์ ์ ๋ฉค๋ฒ๋ง ๋ด์ ์ ํธ๋ฆฌํฐ ํด๋์ค๋ ์ธ์คํด์ค๋ก ๋ง๋ค์ด ์ฐ๋ ค๊ณ ์ค๊ณํ ๊ฒ ์๋๋ค. ๋ฐ๋ผ์ private ์์ฑ์๋ฅผ ์ถ๊ฐํด ํด๋์ค์ ์ธ์คํด์คํ๋ฅผ ๋ง์์ ์ฌ์ฉํ ์ ์๋ค. (์์ฑ์๋ฅผ ๋ช ์ํ์ง ์์ผ๋ฉด ์ปดํ์ผ๋ฌ๊ฐ ์๋์ผ๋ก ๊ธฐ๋ณธ ์์ฑ์๋ฅผ ๋ง๋ ๋ค)
// ์ธ์คํด์ค๋ฅผ ๋ง๋ค ์ ์๋ ์ ํธ๋ฆฌํฐ ํด๋์ค
public class UtilityClass {
// ๊ธฐ๋ณธ ์์ฑ์๊ฐ ๋ง๋ค์ด์ง๋ ๊ฒ์ ๋ง๋๋ค(์ธ์คํด์คํ ๋ฐฉ์ง์ฉ).
// ์
์์ ๋ฆฌํ๋ ์
์ ๋ง์ ์ ์๋ค.
private UtilityClass() {
throw new AssertionError();
}
}
ยท ์์ฑ์๊ฐ ๋ถ๋ช ์กด์ฌํ๋๋ฐ ํธ์ถํ ์๋ ์๋ค๋, ๊ทธ๋ค์ง ์ง๊ด์ ์ด์ง ์์ผ๋ฏ๋ก ์์ ์ฝ๋์ฒ๋ผ ์ ์ ํ ์ฃผ์์ ๋ฌ์์ค๋ค.
ยท ์ด ๋ฐฉ์์ ์์์ ๋ถ๊ฐ๋ฅํ๊ฒ ํ๋ ํจ๊ณผ๋ ์๋ค. ๋ชจ๋ ์์ฑ์๋ ๋ช ์์ ์ด๋ ๋ฌต์์ ์ด๋ ์์ ํด๋์ค๋ฅผ ์์ฑ์๋ฅผ ํธ์ถํด์ผํ๋๋ฐ, ์ด๋ฅผ private ์ ์ธ์ผ๋ก ๋ง์๋ฒ๋ ธ๊ธฐ ๋๋ฌธ์ด๋ค.
์์ดํ
5. ์์์ ์ง์ ๋ช
์ํ์ง ๋ง๊ณ ์์กด ๊ฐ์ฒด ์ฃผ์
์ ์ฌ์ฉํ๋ผ
ยท ๋ง์ ํด๋์ค๊ฐ ํ๋ ์ด์์ ์์์ ์์กดํ๋ค. ์ฌ์ฉํ๋ ์์์ ๋ฐ๋ผ ๋์์ด ๋ฌ๋ผ์ง๋ ํด๋์ค์ ๊ฒฝ์ฐ ํด๋์ค๊ฐ ์ฌ๋ฌ ์์ ์ธ์คํด์ค๋ฅผ ์ง์ํด์ผ ํ๋ฉฐ, ํด๋ผ์ด์ธํธ๊ฐ ์ํ๋ ์์์ ์ฌ์ฉํด์ผ ํ๋ค.
ยท ์ด ์กฐ๊ฑด์ ๋ง์กฑํ๋ ๊ฐ๋จํ ํจํด์ผ๋ก ์ธ์คํด์ค๋ฅผ ์์ฑํ ๋ ์์ฑ์์ ํ์ํ ์์์ ๋๊ฒจ์ฃผ๋ ๋ฐฉ์์ด์๋ค. ์ด๋ ์์กด ๊ฐ์ฒด ์ฃผ์ ์ ํ ํํ๋ค. ์๋๋ ์ฌ์ (dictionary)์ ์์กดํ๋ ๋ง์ถค๋ฒ ๊ฒ์ฌ๊ธฐ ํด๋์ค๋ค.
public class SpellChecker {
private final Lexicon dictionary;
// ์ฌ๊ธฐ์ ์์กด์ฑ ์ฃผ์
์!
public SpellChecker(Lexicon dictionary){
this.dictionary = Objects.requireNotNull(dictionary);
}
public static boolean isVaild(String word) {...}
public static List<String> suggestions(String typo) {...}
}
ยท ์์กด ๊ฐ์ฒด ์ฃผ์ ํจํด์ ์ฅ์ :
1. ์์์ด ๋ช ๊ฐ๋ ์์กด ๊ด๊ณ๊ฐ ์ด๋ป๊ทผ ์๊ด์์ด ์ ๋์ํ๋ค.
2. ๋ถ๋ณ(์์ดํ 17)์ ๋ณด์ฅํ์ฌ ์ฌ๋ฌ ํด๋ผ์ด์ธํธ๊ฐ ์์กด ๊ฐ์ฒด๋ฅผ ์์ฌํ๊ณ ๊ณต์ ํ ์ ์๋๋ก ํ๋ค.
ยท ์์กด ๊ฐ์ฒด ์ฃผ์ ์ ์์ฑ์, ์ ์ ํฉํฐ๋ฆฌ ๋ชจ๋์ ๋๊ฐ์ด ์์ฉํ ์ ์๋ค.
ยท ์ด ํจํด์ ์ธ๋งํ ๋ณํ์ผ๋ก, ์์ฑ์์ ์์ ํฉํฐ๋ฆฌ๋ฅผ ๋๊ฒจ์ฃผ๋ ๋ฐฉ์์ด ์๋ค. ์ฆ, ํฉํฐ๋ฆฌ ๋ฉ์๋ ํจํด(Gamma95)์ ๊ตฌํํ๋ ๊ฒ์ด๋ค.
- ํฉํฐ๋ฆฌ: ํธ์ถํ ๋๋ง๋ค ํน์ ํ์ ์ ์ธ์คํด์ค๋ฅผ ๋ฐ๋ณตํด์ ๋ง๋ค์ด์ฃผ๋ ๊ฐ์ฒด
ยท ์๋ฐ 8์์ ์๊ฐํ Supplier<T> ์ธํฐํ์ด์ค๋ ํฉํฐ๋ฆฌ๋ฅผ ํํํ ์๋ฒฝํ ์๋ค.
ยท Supplier<T>๋ฅผ ์ ๋ ฅ์ผ๋ก ๋ฐ๋ ๋ฉ์๋๋ ์ผ๋ฐ์ ์ผ๋ก ํ์ ์ ์์ผ๋์นด๋ ํ์ (bounded wildcard type, ์์ดํ 31)์ ์ฌ์ฉํด ํฉํฐ๋ฆฌ์ ํ์ ๋งค๊ฐ๋ณ์๋ฅผ ์ ํํด์ผํ๋ค. ์ด ๋ฐฉ์์ ์ฌ์ฉํด ํด๋ผ์ด์ธํธ๋ ์์ ์ด ๋ช ์ํ ํ์ ์ ํ์ ํ์ ์ด๋ผ๋ฉด ๋ฌด์์ด๋ ์์ฑํ ์ ์๋ ํฉํฐ๋ฆฌ๋ฅผ ๋๊ธธ ์ ์๋ค.
- ์์) ํด๋ผ์ด์ธํธ๊ฐ ์ ๊ณตํ ํฉํฐ๋ฆฌ๊ฐ ์์ฑํ ํ์ผ๋ค๋ก ์ฟ ์ฑ๋ ๋ชจ์์ดํฌ๋ฅผ ๋ง๋๋ ๋ฉ์๋
Mosaic create(Supplier<? extends Tile> tileFactory) { ... }
ยท ์์กด ๊ฐ์ฒด ์ฃผ์ ์ ์ ์ฐ์ฑ๊ณผ ํ ์คํธ ์ฉ์ด์ฑ์ ๊ฐ์ ํด์ค๋ค.
ยท ํ์ง๋ง ์์กด์ฑ์ด ๋ง์ ํฐ ํ๋ก์ ํธ์์๋ ์ฝ๋๋ฅผ ์ด์ง๋ฝ๊ฒ ๋ง๋ค๊ธฐ๋ ํ๋ค. ์ด๋ด๋ ๋๊ฑฐ, ์ฃผ์ค, ์คํ๋ง ๊ฐ์ ์์กด ๊ฐ์ฒด ์ฃผ์ ํ๋ ์์ํฌ๋ฅผ ์ฌ์ฉํ์ฌ ์ด ๋ฌธ์ ๋ฅผ ํด๊ฒฐํ ์ ์๋ค.
ยท ํด๋์ค๊ฐ ๋ด๋ถ์ ์ผ๋ก ํ๋ ์ด์์ ์์์ ์์กดํ๊ณ , ๊ทธ ์์์ด ํด๋์ค ๋์์ ์ํฅ์ ์ค๋ค๋ฉด ์ฑ๊ธํด๊ณผ ์ ์ ์ ํธ๋ฆฌํฐ ํด๋์ค๋ ์ฌ์ฉํ์ง ์๋ ๊ฒ์ด ์ข๋ค. ์ด ์์๋ค์ ํด๋์ค๊ฐ ์ง์ ๋ง๋ค๊ฒ ํด์๋ ์๋๋ค.
- ์ ์ ์ ํธ๋ฆฌํฐ๋ฅผ ์๋ชป ์ฌ์ฉํ ์: ์ ์ฐํ์ง ์๊ณ ํ ์คํธํ๊ธฐ ์ด๋ ต๋ค.
public class SpellChecker {
private static final Lexicon dictionary = ...;
private SpellChecker() {} // ์ธ์คํด์คํ ๋ฐฉ์ง (์์ดํ
4 ์ฐธ๊ณ )
public static boolean isVaild(String word) {...}
public static List<String> suggestions(String typo) {...}
}
- ์ฑ๊ธํด์ ์๋ชป ์ฌ์ฉํ ์: ์ ์ฐํ์ง ์๊ณ ํ ์คํธํ๊ธฐ ์ด๋ ต๋ค.
public class SpellChecker {
private final Lexicon dictionary = ...;
private SpellChecker() {} // ์ธ์คํด์คํ ๋ฐฉ์ง (์์ดํ
4 ์ฐธ๊ณ )
public static SpellChecker INSTANCE = new SpellChecker(...);
public static boolean isVaild(String word) {...}
public static List<String> suggestions(String typo) {...}
}
์์ดํ
6. ๋ถํ์ํ ๊ฐ์ฒด ์์ฑ์ ํผํ๋ผ
ยท ๋๊ฐ์ ๊ธฐ๋ฅ์ ๊ฐ์ฒด๋ฅผ ๋งค๋ฒ ์์ฑํ๊ธฐ๋ณด๋ค ๊ฐ์ฒด ํ๋๋ฅผ ์ฌ์ฌ์ฉํ๋ ํธ์ด ๋์ ๋๊ฐ ๋ง๋ค. ์ฌ์ฌ์ฉ์ ๋น ๋ฅด๊ณ ์ธ๋ จ๋๋ค. ํนํ ๋ถ๋ณ ๊ฐ์ฒด(์์ดํ 17)๋ ์ธ์ ๋ ์ฌ์ฌ์ฉํ ์ ์๋ค.
ยท ์์ฑ์ ๋์ ์ ์ ํฉํฐ๋ฆฌ ๋งค์๋๋ฅผ ์ ๊ณตํ๋ ๋ถ๋ณ ํด๋์ค์์๋ ๋ถํ์ํ ๊ฐ์ฒด ์์ฑ์ ํผํ ์ ์๋ค.
ex) Boolean(String) ์์ฑ์ ๋์ Boolean.valueOf(String) ํฉํฐ๋ฆฌ ๋ฉ์๋๋ฅผ ์ฌ์ฉํ๋ ๊ฒ์ด ์ข๋ค.
ยท ๊ฐ๋ณ ๊ฐ์ฒด๋ผ ํด๋ ์์ฉ ์ค์ ๋ณ๊ฒฝ๋์ง ์์ ๊ฒ์์ ์๋ค๋ฉด ์ฌ์ฌ์ฉํ ์ ์๋ค.
ยท ์์ฑ ๋น์ฉ์ด ์์ฃผ ๋น์ผ ๊ฐ์ฒด๊ฐ ๋ฐ๋ณตํด์ ํ์ํ๋ค๋ฉด, ์บ์ฑํ์ฌ ์ฌ์ฌ์ฉํ๊ธธ ๊ถํ๋ค.
ex) ์๋๋ ์ฃผ์ด์ง ๋ฌธ์์ด์ด ์ ํจํ ๋ก๋ง ์ซ์์ธ์ง ํ์ธํ๋ ๋ฉ์๋๋ค. ํ์ง๋ง String.matches ๋ฉ์๋๋ฅผ ์ฌ์ฉํ๋ค๋ ๋ฐ ๋ฌธ์ ๊ฐ ์๋ค.
public class RomanNumerals {
static boolean isRomanNumeral(String s) {
return s.matches("^(?=.)M*(C[MD]|D?C{0,3})" +
"(X[CL]|L?X{0,3})(I[XV]|V?I{0,3})");
}
}
- String.matches๋ ์ฑ๋ฅ์ด ์ค์ํ ์ํฉ์์ ๋ฐ๋ณตํด ์ฌ์ฉํ๊ธฐ์ ์ ํฉํ์ง ์๋ค.
1. ๋ฉ์๋ ๋ด๋ถ์์ ๋ง๋๋ ์ ๊ทํํ์์ฉ Pattern ์ธ์คํด์ค๋ ํ ๋ฒ ์ฐ๊ณ ๋ฒ๋ ค์ ธ์ ๊ณง๋ฐ๋ก ๊ฐ๋น์ง ์ปฌ๋ ์ ๋์์ด ๋๋ค.
2. Pattern์ ์ ๋ ฅ๋ฐ์ ์ ๊ทํํ์์ ํด๋นํ๋ ์ ํ ์ํ ๋จธ์ (finite state machine)์ ๋ง๋ค๊ธฐ ๋๋ฌธ์ ์ธ์คํด์ค ์์ฑ ๋น์ฉ์ด ๋๋ค.
TODO: ์ ํ ์ํ ๋จธ์ ์ด๋?
- ๋ถ๋ณ์ธ Pattern ์ธ์คํด์ค๋ฅผ ํด๋์ค ์ด๊ธฐํ(์ ์ ์ด๊ธฐํ) ๊ณผ์ ์์ ์ง์ ์์ฑํด ์บ์ฑํด๋๊ณ , ์ฌ์ฌ์ฉํ ์ ์๋ค.
์๋ ์ฝ๋๋ ์ฑ๋ฅ๋ง ์ข์์ง ๊ฒ์ด ์๋๋ผ ์ฝ๋๋ ๋ ๋ช ํํด์ก๋ค.
public class RomanNumerals {
private static final Pattern ROMAN = Pattern.compile("^(?=.)M*(C[MD]|D?C{0,3})" +
"(X[CL]|L?X{0,3})(I[XV]|V?I{0,3})");
static boolean isRomanNumeral(String s) {
return ROMAN.matcher(s).matches();
}
}
- isRomanNumeral ๋ฉ์๋๊ฐ ์ฒ์ ํธ์ถ๋ ๋ ํ๋๋ฅผ ์ด๊ธฐํํ๋๋ก ์ง์ฐ ์ด๊ธฐํ๋ก ๋ถํ์ํ ์ด๊ธฐํ๋ฅผ ์์จ ์๋ ์์ง๋ง, ๊ถํ์ง ์๋๋ค.
- ์ง์ฐ ์ด๊ธฐํ๋ ์ฝ๋๋ฅผ ๋ณต์กํ๊ฒ ๋ง๋๋๋ฐ, ์ฑ๋ฅ์ ํฌ๊ฒ ๊ฐ์ ๋์ง ์์ ๋๊ฐ ๋ง๋ค(์์ดํ 67).
ยท ๊ฐ์ฒด๊ฐ ๋ถ๋ณ์ด๋ผ๋ฉด ์ฌ์ฌ์ฉํด๋ ์์ ํจ์ด ๋ช ๋ฐฑํ์ง๋ง, ํจ์ฌ ๋ ๋ช ํํ๊ฑฐ๋, ์ง๊ด์ ๋ฐ๋๋๋ ์ํฉ๋ ์๋ค.
ex) ์ด๋ํฐ[Gamma95]๋ฅผ ์๋ก ๋ค๋ฉด, ์ด๋ํฐ๋ ์ธํฐํ์ด์ค๋ฅผ ํตํด ๋ค์ ์๋ ๊ฐ์ฒด๋ก ์ฐ๊ฒฐํด์ฃผ๋ view๋ผ ์ฌ๋ฌ ๊ฐ ๋ง๋ค ํ์๊ฐ ์๋ค.
- ์ด๋ํฐ: ์ค์ ์์ ์ ๋ท๋จ ๊ฐ์ฒด์ ์์ํ๊ณ , ์์ ์ ์ 2์ ์ธํฐํ์ด์ค ์ญํ ์ ํด์ฃผ๋ ๊ฐ์ฒด
๋ค์๊ณผ ๊ฐ์ด ๊ฐ์ ์ธ์คํด์ค๋ฅผ ๋๋ณํ๋ ์ฌ๋ฌ ๊ฐ์ ์ธ์คํด์ค๋ฅผ ์์ฑํ์ง ๋ง์.
Map<String, Object> map = new HashMap<>();
map.put("Hello", "World");
Set<String> set1 = map.keySet();
Set<String> set2 = map.keySet();
assertThat(set1).isSameAs(set2); // TRUE
set1.remove("Hello");
System.out.println(set1.size()); // 1
System.out.println(set1.size()); // 1
ยท ์คํ ๋ฐ์ฑ์ ๋ถํ์ํ ๊ฐ์ฒด๋ฅผ ๋ง๋ค์ด ์ฑ๋ฅ์ ํด๋ก์ธ ์ ์๋ค.
- ์คํ ๋ฐ์ฑ: ํ๋ก๊ทธ๋๋จธ๊ฐ ๊ธฐ๋ณธ ํ์ ๊ณผ ๋ฐ์ฑ๋ ๊ธฐ๋ณธ ํ์ ์ ์์ด ์ธ ๋ ์๋์ผ๋ก ์ํธ ๋ณํํด์ฃผ๋ ๊ธฐ์
ex) ๋ค์์ sum ๋ณ์๋ฅผ long์ด ์๋ Long์ผ๋ก ์ ์ธํด์ ๋ถํ์ํ Long ์ธ์คํด์ค๊ฐ ์ฝ 231๊ฐ๋ ๋ง๋ค์ด ์ง๋ค.
public class Sum {
private static long sum() {
Long sum = 0L;
for (long i = 0; i <= Integer.MAX_VALUE; i++) {
sum += i;
}
return sum;
}
}
ยท ๊ฐ์ฒด ์์ฑ์ ๋ฌด์กฐ๊ฑด ๋น์ธ๋ ํผํด์ผ ํ๋ ๊ฒ์ ์๋๋ค. ํ๋ก๊ทธ๋จ์ ๋ช ํ์ฑ, ๊ฐ๊ฒฐ์ฑ, ๊ธฐ๋ฅ์ ์ํด ๊ฐ์ฒด๋ฅผ ์ถ๊ฐ๋ก ์์ฑํ๋ ๊ฒ์ ์ผ๋ฐ์ ์ผ๋ก ์ข๋ค.
ยท ๋ฐ์ดํฐ๋ฒ ์ด์ค ์ฐ๊ฒฐ ๊ฐ์ ์์ฑ ๋น์ฉ์ด ๋งค์ฐ ๋น์ผ ๊ฒฝ์ฐ๊ฐ ์๋๋ผ๋ฉด ๊ฐ์ฒด ํ์ ๋ง๋ค์ง ๋ง์. ์ผ๋ฐ์ ์ผ๋ก ์์ฒด ๊ฐ์ฒด ํ์ ์ฝ๋๋ฅผ ํท๊ฐ๋ฆฌ๊ฒ ๋ง๋ค๊ณ , ์ฌ์ฉ๋์ ๋๋ฆฌ๊ณ , ์ฑ๋ฅ์ ๋จ์ด๋จ๋ฆฐ๋ค.
ยท ์ด๋ฒ ์์ดํ ์ ๋ฐฉ์ด์ ๋ณต์ฌ(defensive copy)๋ฅผ ๋ค๋ฃจ๋ ์์ดํ 50๊ณผ ๋์กฐ์ ์ด๋ค.
- ๊ธฐ์กด ๊ฐ์ฒด๋ฅผ ์ฌ์ฌ์ฉํด์ผ ํ๋ค๋ฉด ์๋ก์ด ๊ฐ์ฒด๋ฅผ ๋ง๋ค์ง ๋ง๋ผ vs ์๋ก์ด ๊ฐ์ฒด๋ฅผ ๋ง๋ค์ด์ผ ํ๋ค๋ฉด ๊ธฐ์กด ๊ฐ์ฒด๋ฅผ ์ฌ์ฌ์ฉํ์ง ๋ง๋ผ
- ๋ฐฉ์ด์ ๋ณต์ฌ๊ฐ ํ์ํ ์ํฉ์์ ๊ฐ์ฒด๋ฅผ ์ฌ์ฌ์ฉํ์ ๋ ํผํด๊ฐ ํ์ ์๋ ๊ฐ์ฒด๋ฅผ ๋ฐ๋ณต ์์ฑํ์ ๋ ํผํด๋ณด๋ค ํจ์ฌ ํฌ๋ค.
- ๋ฐฉ์ด์ ๋ณต์ฌ์ ์คํจํ๋ฉด ๋ฒ๊ทธ์ ๋ณด์ ๊ตฌ๋ฉ์ผ๋ก ์ด์ด์ง์ง๋ง, ๋ถํ์ํ ๊ฐ์ฒด ์์ฑ์ ๊ทธ์ ์ฝ๋ ํํ์ ์ฑ๋ฅ์๋ง ์ํฅ์ ์ค๋ค.
์์ดํ
7. ๋ค ์ด ๊ฐ์ฒด ์ฐธ์กฐ๋ฅผ ํด์ ํ๋ผ
ยท ์๋ ์คํ ํด๋์ค๋ ๋ฉ๋ชจ๋ฆฌ ๋์๊ฐ ๋ฐ์ํ๋ค.
- ์ด ์คํ์ ์ฌ์ฉํ๋ ํ๋ก๊ทธ๋จ์ ์ค๋ ์คํํ๋ค ๋ณด๋ฉด ์ ์ฐจ ๊ฐ๋น์ง ์ปฌ๋ ์ ํ๋๊ณผ ๋ฉ๋ชจ๋ฆฌ ์ฌ์ฉ๋์ด ๋์ด๋ ๊ฒฐ๊ตญ ์ฑ๋ฅ์ด ์ ํ๋๋ค.
- ๋๋ฌผ๊ธด ํ์ง๋ง ์ฌํ ๋๋ ๋์คํฌ ํ์ด์ง์ด๋ OutOfMemoryError๋ฅผ ์ผ์ผ์ผ ํ๋ก๊ทธ๋จ์ด ์๊ธฐ์น ์๊ฒ ์ข ๋ฃ๋๋ค.
public class Stack {
private Object[] elements;
private int size = 0;
private static final int DEFAULT_INITIAL_CAPACITY = 16;
public Stack() {
elements = new Object[DEFAULT_INITIAL_CAPACITY];
}
public void push(Object e) {
ensureCapacity();
elements[size++] = e;
}
public Object pop() {
if (size == 0) {
throw new EmptyStackException();
}
return elements[--size];
}
private void ensureCapacity() {
if (elements.length == size) {
elements = Arrays.copyOf(elements, 2 * size + 1);
}
}
}
ยท pop ๋ฉ์๋์์ ๋ฉ๋ชจ๋ฆฌ ๋์๊ฐ ๋ฐ์ํ๋ค.
- ์คํ์ด ์ปค์ก๋ค๊ฐ ์ค์ด๋ค ๋, ์คํ์์ ๊บผ๋ด์ง ๊ฐ์ฒด๋ค์ ํ๋ก๊ทธ๋จ์์ ๋ ์ด์ ์ฌ์ฉํ์ง ์๋๋ผ๋ ๊ฐ๋น์ง ์ปฌ๋ ํฐ๊ฐ ํ์ํ์ง ์๋๋ค.
- ๊บผ๋ด์ง ๊ฐ์ฒด๋ค์ด ๋ค ์ด ์ฐธ์กฐ(obsolete reference)๋ฅผ ์ฌ์ ํ ๊ฐ์ง๊ณ ์๊ธฐ ๋๋ฌธ์ด๋ค.
- elements ๋ฐฐ์ด์ 'ํ์ฑ ์์ญ'๋ฐ์ ์ฐธ์กฐ๋ค์ด ๋ชจ๋ ์ฌ๊ธฐ์ ํด๋นํ๋ค. ํ์ฑ ์์ญ์ ์ธ๋ฑ์ค๊ฐ size๋ณด๋ค ์์ ์์๋ค๋ก ๊ตฌ์ฑ๋๋ค.
- ๋ค์ด ์ฐธ์กฐ: ์์ผ๋ก ๋ค์ ์ฐ์ง ์์ ์ฐธ์กฐ
ยท ๊ฐ์ฒด ์ฐธ์กฐ ํ๋๋ฅผ ์ด๋ ค๋๋ฉด ๊ฐ๋น์ง ์ปฌ๋ ํฐ๋ ๊ทธ ๊ฐ์ฒด๋ฟ ์๋๋ผ ๊ทธ ๊ฐ์ฒด๊ฐ ์ฐธ์กฐํ๋ ๋ชจ๋ ๊ฐ์ฒด(๋ ๊ทธ ๊ฐ์ฒด๋ค์ด ์ฐธ์กฐํ๋ ๋ชจ๋ ๊ฐ์ฒด)๋ฅผ ํ์ํด๊ฐ์ง ๋ชปํ๋ค.
- ๋จ ๋ช ๊ฐ์ ๊ฐ์ฒด๊ฐ ๋งค์ฐ ๋ง์ ๊ฐ์ฒด๋ฅผ ํ์๋์ง ๋ชปํ๊ฒ ํ ์ ์๊ณ , ์ ์ฌ์ ์ผ๋ก ์ฑ๋ฅ์ ์ ์ํฅ์ ์ค ์ ์๋ค.
ํด๊ฒฐ ๋ฐฉ๋ฒ
ยท ์ฐธ์กฐ๋ฅผ ๋ค ์ผ์ ๋ null(์ฐธ์กฐ ํด์ )ํ๋ค.
public Object pop() {
if (size == 0)
throw new EmptyStackException();
Object result = elements[--size];
elements[size] = null; // ๋ค ์ด ์ฐธ์กฐ ํด์
return result;
}
ยท ๋ค์ด ์ฐธ์กฐ๋ฅผ null ํ๋ฉด ํ๋ก๊ทธ๋จ ์ค๋ฅ๋ฅผ ์กฐ๊ธฐ์ ๋ฐ๊ฒฌํ ์๋ ์๋ค.
- null ์ฒ๋ฆฌํ ์ฐธ์กฐ๋ฅผ ์ค์๋ก ์ฌ์ฉํ๋ ค ํ๋ฉด ํ๋ก๊ทธ๋จ์ ์ฆ์ NullPointerException์ ๋์ง๋ฉฐ ์ข ๋ฃ๋๋ค.
- null ์ฒ๋ฆฌํ์ง ์์๋ค๋ฉด, ์๋ฌด ๋ด์ ์์ด ๋ฌด์ธ๊ฐ ์๋ชป๋ ์ผ์ ์ํํ ์ ์๋ค.
ยท ๊ฐ์ฒด ์ฐธ์กฐ๋ฅผ null ์ฒ๋ฆฌํ๋ ์ผ์ ์์ธ์ ์ธ ๊ฒฝ์ฐ์ฌ์ผ ํ๋ค. ๋ค ์ด ์ฐธ์กฐ๋ฅผ ํด์ ํ๋ ๊ฐ์ฅ ์ข์ ๋ฐฉ๋ฒ์ ๊ทธ ์ฐธ์กฐ๋ฅผ ๋ด์ ๋ณ์๋ฅผ ์ ํจ ๋ฒ์(scope) ๋ฐ์ผ๋ก ๋ฐ์ด๋ด๋ ๊ฒ์ด๋ค.
- ๋ณ์์ ๋ฒ์๋ฅผ ์ต์๋ก ๋๊ฒ ์ ์ํ๋ค๋ฉด(์์ดํ 57) ์ด ์ผ์ ์์ฐ์ค๋ฝ๊ฒ ์ด๋ค์ง๋ค.
- null ์ฒ๋ฆฌ๋ฅผ ํด์ผํ๋ ๊ฒฝ์ฐ๋ ์์ ์ฝ๋์ ์คํ ์ฒ๋ผ ์๊ธฐ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ์ง์ ๊ด๋ฆฌํ๋ ํด๋์ค์ด๋ค. ๋นํ์ฑ ์์ญ์์ ์ฐธ์กฐํ๋ ๊ฐ์ฒด๊ฐ ๋ ์ด์ ์ธ๋ชจ์๋ค๋ ๊ฒ์ ํ๋ก๊ทธ๋๋จธ๋ง ์์ง ๊ฐ๋น์ง ์ปฌ๋ ํฐ๋ ์์ง ๋ชปํ๊ธฐ ๋๋ฌธ์ด๋ค. ์ด๋ด ๋๋ null ์ฒ๋ฆฌ๋ฅผ ํ์ฌ ๊ฐ๋น์ง ์ปฌ๋ ํฐ์ ์ง์ ์๋ ค์ผํ๋ค.
ยท ์บ์ ์ญ์ ๋ฉ๋ชจ๋ฆฌ ๋์๋ฅผ ์ผ์ผํค๋ ์ฃผ๋ฒ์ด๋ค.
- ๊ฐ์ฒด ์ฐธ์กฐ๋ฅผ ๋ค ์ด ๋ค ํจ์ฐธ์ ๊ทธ๋ฅ ๋๋๋ ์ผ์ ์์ฃผ ์ ํ ์ ์๋ค.
- ํด๊ฒฐ ๋ฐฉ๋ฒ1: ์ธ๋ถ์์ ํค๋ฅผ ์ฐธ์กฐํ๋ ๋์๋ง ์ํธ๋ฆฌ๊ฐ ์ด์ ์๋ ์บ์๊ฐ ํ์ํ๋ค๋ฉด, WeakHashMap์ ์ฌ์ฉํด ์บ์๋ฅผ ๋ง๋ ๋ค.
๋ค ์ด ์ํธ๋ฆฌ๋ ์ฆ์ ์๋์ผ๋ก ์ ๊ฑฐ๋๋ค.
- ํด๊ฒฐ ๋ฐฉ๋ฒ2: ์บ์๋ฅผ ๋ง๋ค ๋ ๋ณดํต ์บ์ ์ํธ๋ฆฌ์ ์ ํจ ๊ธฐ๊ฐ์ ์ ํํ ์ ์ํ๊ธฐ ์ด๋ ต๊ธฐ ๋๋ฌธ์ ์๊ฐ์ด ์ง๋ ์๋ก ์ํธ๋ฆฌ์ ๊ฐ์น๋ฅผ ๋จ์ด๋จ๋ฆฌ๋ ๋ฐฉ์์ด ํํ ์ฌ์ฉ๋๋ค. ์ด๋ฐ ๋ฐฉ์์์๋ ์ฐ์ง ์๋ ์ํธ๋ฆฌ๋ฅผ ์ด๋ฐ๊ธ ์ฒญ์ํด์ผํ๋ค. ScheduledThreadPoolExecutor ๊ฐ์ ๋ฐฑ๊ทธ๋ผ์ด๋ ์ค๋ ๋๋ฅผ ํ์ฉํ๊ฑฐ๋ ์บ์์ ์ ์ํธ๋ฆฌ๋ฅผ ์ถ๊ฐํ ๋ ๋ถ์ ์์ ์ผ๋ก ์ํํ ์ ์๋ค.
- LinkedHahshMap์ removeEldestEntry ๋ฉ์๋๋ฅผ ์จ์ ํ์์ ๋ฐฉ์์ผ๋ก ์ฒ๋ฆฌํ๋ค.
- ๋ ๋ณต์กํ ์บ์๋ฅผ ๋ง๋ค๊ณ ์ถ๋ค๋ฉด java.lang.ref ํจํค์ง๋ฅผ ์ง์ ํ์ฉํด์ผ ํ๋ค.
์์ดํ
8. finalizer์ cleaner ์ฌ์ฉ์ ํผํ๋ผ
ยท ์๋ฐ๋ finalizer, cleaner ๋ ๊ฐ์ง ๊ฐ์ฒด ์๋ฉธ์๋ฅผ ์ ๊ณตํ๋ค.
ยท finalizer๋ ์์ธกํ ์ ์๊ณ , ์ํฉ์ ๋ฐ๋ผ ์ํํ ์ ์์ด ์ผ๋ฐ์ ์ผ๋ก ๋ถํ์ํ๋ค.
- ์ค๋์, ๋ฎ์ ์ฑ๋ฅ, ์ด์์ฑ ๋ฌธ์ ์ ์์ธ์ด ๋๊ธฐ๋ ํ๋ค.
ยท ์๋ฐ 9์์ finalizer๊ฐ deprecated๋๊ณ , cleaner๋ฅผ ๊ทธ ๋์์ผ๋ก ์๊ฐํ์ง๋ง, ์ฌ์ ํ ์์ธกํ ์ ์๊ณ , ๋๋ฆฌ๊ณ , ์ผ๋ฐ์ ์ผ๋ก ๋ถํ์ํ๋ค.
ยท C++์์์ ํ๊ดด์(destructor)์ ์๋ฐ์ finalizer, cleaner๋ ๋ค๋ฅธ ๊ฐ๋ ์ด๋ค.
- C++์ ํ๊ดด์๋ ๋น๋ฉ๋ชจ๋ฆฌ ์์์ ํ์ํ๋ ์ฉ๋๋ก ์ฐ์ด๊ณ , ์๋ฐ์์๋ try-with-resources์ try-finally๋ฅผ ์ฌ์ฉํด ํด๊ฒฐํ๋ค.
finalizer์ cleaner์ ๋ถ์์ฉ
ยท finalizer์ cleaner๋ ์ฆ์ ์ํ๋๋ค๋ ๋ณด์ฅ์ด ์๊ณ , ์คํ๋๊ธฐ๊น์ง ์ผ๋ง๋ ๊ฑธ๋ฆด์ง ์ ์ ์๋ค.
- ๋ฐ๋ผ์ ํ์ผ ๋ซ๊ธฐ์ ๊ฐ์ด ์ ๋ ์คํ๋์ด์ผ ํ๋ ์์ ์ ๋์๊ฒ ๋งก๊ธฐ๋ฉด ์ค๋ํ ์ค๋ฅ๋ฅผ ์ผ์ผํฌ ์ ์๋ค. ์์คํ ์ด ๋์์ ์ด ์ ์๋ ํ์ผ ๊ฐ์์ ํ๊ณ๊ฐ ์๊ธฐ ๋๋ฌธ์ด๋ค. ์๋ก์ด ํ์ผ์ ์ด์ง ๋ชปํด ํ๋ก๊ทธ๋จ์ด ์คํจํ ์ ์๋ค.
ยท ์๋ฐ ์ธ์ด ๋ช ์ธ๋ finalizer๋ clearner์ ์ํ ์์ ๋ฟ ์๋๋ผ ์ํ ์ฌ๋ถ์กฐ์ฐจ ๋ณด์ฅํ์ง ์๋๋ค.
ยท System.gc๋ System.runFinalization ๋ฉ์๋๊ฐ finalize์ cleaner๊ฐ ์คํ๋ ๊ฐ๋ฅ์ฑ์ ๋์ฌ์ค ์๋ ์์ง๋ง, ๋ณด์ฅํด์ฃผ์ง ์๋๋ค.
- System.runFinalizerOnExit๊ณผ Runtime.runFinalizerOnExit ๋ฉ์๋๊ฐ ์ด๋ฅผ ๋ณด์ฅํด์ค ์ ์์ง๋ง, ๋ ๋ฉ์๋๋ ThreadStop์ด๋ผ๋ ์ฌ๊ฐํ ๊ฒฐํจ์ด ์๋ค.
ยท finalizer ๋์ ์ค ๋ฐ์ํ ์์ธ๋ ๋ฌด์๋๋ฉฐ, ์ฒ๋ฆฌํ ์์ ์ด ๋จ์๋๋ผ๋ ๊ทธ ์๊ฐ ์ข ๋ฃ๋๋ค. ๊ฒฝ๊ณ ์กฐ์ฐจ ์ถ๋ ฅํ์ง ์๋๋ค.
- ํด๋น ๊ฐ์ฒด๋ ๋ง๋ฌด๋ฆฌ๊ฐ ๋ ๋ ์ํ๋ก ๋จ์ ๋ค๋ฅธ ์ค๋ ๋์์ ํผ์๋ ๊ฐ์ฒด๋ฅผ ์ฌ์ฉํ ์๋ ์๋ค.
(cleaner๋ฅผ ์ฌ์ฉํ๋ ๋ผ์ด๋ธ๋ฌ๋ฆฌ๋ ์์ ์ ์ค๋ ๋๋ฅผ ํต์ ํ๋ฏ๋ก ์ด๋ฐ ๋ฌธ์ ๋ ๋ฐ์ x)
ยท finalizer์ cleaner๋ ์ฌ๊ฐํ ์ฑ๋ฅ ๋ฌธ์ ๋ฅผ ๋๋ฐํ๋ค.
- ์ ์์ ์ปดํจํฐ์์ AutoCloseable ๊ฐ์ฒด๋ฅผ ์์ฑํ๊ณ ๊ฐ๋น์ง ์ปฌ๋ ํฐ๊ฐ ์๊ฑฐํ๊ธฐ๊น์ง 12ns๊ฐ ๊ฑธ๋ฆฐ ๋ฐ๋ฉด, finalizer๋ฅผ ์ฌ์ฉํ๋ฉด 550ns๊ฐ ๊ฑธ๋ ธ๋ค. cleaner๋ ์ด์ ๋น์ทํ๋ค.
ยท finalizer๋ฅผ ์ฌ์ฉํ ํด๋์ค๋ finalizer ๊ณต๊ฒฉ์ ๋ ธ์ถ๋์ด ์ฌ๊ฐํ ๋ณด์ ๋ฌธ์ ๋ฅผ ์ผ์ผํฌ ์ ์๋ค.
- finalizer ๊ณต๊ฒฉ: ์์ฑ์๋ ์ง๋ ฌํ ๊ณผ์ ์์ ์์ธ๊ฐ ๋ฐ์ํ๋ฉด, ์์ฑ๋๋ค ๋ง ๊ฐ์ฒด์์ ์ ์์ ์ธ ํ์ ํด๋์ค์ finalizer๊ฐ ์ํ๋ ์ ์๊ฒ ๋๋ค.
- ์ด finalizer๋ ์ ์ ํ๋์ ์์ ์ ์ฐธ์กฐ๋ฅผ ํ ๋นํ์ฌ ๊ฐ๋น์ง ์ปฌ๋ ํฐ๊ฐ ์์ง ๋ชปํ๊ฒ ๋ง์ ์ ์๋ค.
- ์ด๋ ๊ฒ ์ผ๊ทธ๋ฌ์ง ๊ฐ์ฒด๊ฐ ๋ง๋ค์ด์ง๋ฉด, ์ด ๊ฐ์ฒด์ ๋ฉ์๋๋ฅผ ํธ์ถํด์ ํ์ฉ๋์ง ์์ ์์ ์ ์ํํ ์ ์๋ค.
- ๋ฐฉ์ด ๋ฐฉ๋ฒ1: final ํด๋์ค๋ ํ์ ํด๋์ค๋ฅผ ๋ง๋ค ์ ์์ด ์ด ๊ณต๊ฒฉ์์ ์์ ํ๋ค.
- ๋ฐฉ์ด ๋ฐฉ๋ฒ2: final์ด ์๋ ํด๋์ค๋ฅผ finalizer ๊ณต๊ฒฉ์ผ๋ก๋ถํฐ ๋ฐฉ์ดํ๋ ค๋ฉด, ์๋ฌด ์ผ๋ ํ์ง ์๋ finalize ๋ฉ์๋๋ฅผ ๋ง๋ค๊ณ final ๋ก ์ฑ์ธํ์.
์ข ๋ฃํด์ผ ํ ์์์ ๋ด๊ณ ์๋ ๊ฐ์ฒด์ ํด๋์ค(ํ์ผ์ด๋ ์ค๋ ๋ ๋ฑ)์์ finalizer์ Cleaner๋ฅผ ๋์ ํ๋ ๋ฐฉ๋ฒ
ยท AutoCloseable์ ๊ตฌํํ๊ณ , ํด๋ผ์ด์ธํธ์์ ์ธ์คํด์ค๋ฅผ ๋ค ์ฐ๊ณ ๋๋ฉด close ๋ฉ์๋๋ฅผ ํธ์ถํ๋ค.
- ์ผ๋ฐ์ ์ผ๋ก ์์ธ๊ฐ ๋ฐ์ํด๋ ์ ๋๋ก ์ข ๋ฃ๋๋๋ก try-with-resources ์ฌ์ฉ
ยท ๊ฐ ์ธ์คํด์ค๋ ์์ ์ด ๋ซํ๋์ง ์ถ์ ํ๋ ๊ฒ์ด ์ข๋ค.
- ์ฆ, close ๋ฉ์๋์์ ์ด ๊ฐ์ฒด๋ ๋ ์ด์ ์ ํจํ์ง ์์์ ํ๋์ ๊ธฐ๋กํ๊ณ , ๋ค๋ฅธ ๋ฉ์๋๋ ์ด ํ๋๋ฅผ ๊ฒ์ฌํด์ ๊ฐ์ฒด๊ฐ ๋ซํ ํ์ ๋ถ๋ ธ๋ค๋ฉด IllegalStateException์ ๋์ง๋ค.
finalizer์ Cleaner์ ์ฉ๋
1. ์์์ ์์ ์๊ฐ close ๋ฉ์๋๋ฅผ ํธ์ถํ์ง ์๋ ๊ฒ์ ๋๋นํ ์์ ๋ง ์ญํ ์ ํ๋ค.
- finalizer๋ cleaner๊ฐ ์ฆ์ ํธ์ถ๋๋ฆฌ๋ผ๋ ๋ณด์ฅ์ ์์ง๋ง, ํด๋ผ์ด์ธํธ๊ฐ ํ์ง ์์ ์์ ํ์๋ฅผ ์์ ์ํ๋ ๊ฒ๋ณด๋ค๋ ๋ซ๋ค.
- FileInputStream, FileOutputStream, ThreadPoolExecutor ๋ฑ ์๋ฐ๋ผ์ด๋ธ๋ฌ๋ฆฌ ์ผ๋ถ์์ ์์ ๋ง ์ญํ ์ finalizer๋ฅผ ์ ๊ณตํ๋ค.
2. ๋ค์ดํฐ๋ธ ํผ์ด์ ์ฐ๊ฒฐ๋ ๊ฐ์ฒด์์ ์์ ํ์์ฉ์ผ๋ก ์ฌ์ฉํ๋ค.
- ๋ค์ดํฐ๋ธ ํผ์ด: ์ผ๋ฐ ์๋ฐ ๊ฐ์ฒด๊ฐ ๋ค์ดํฐ๋ธ ๋ฉ์๋๋ฅผ ํตํด ๊ธฐ๋ฅ์ ์์ํ ๋ค์ดํฐ๋ธ ๊ฐ์ฒด๋ค. ์๋ฐ ๊ฐ์ฒด๊ฐ ์๋๋ฏ๋ก, ๊ฐ๋น์ง ์ปฌ๋ ํฐ๋ ๊ทธ ์กด์ฌ๋ฅผ ์์ง ๋ชปํ๋ค.
- ์ฑ๋ฅ ์ ํ๋ฅผ ๊ฐ๋นํ ์ ์๊ณ , ๋ค์ดํฐ๋ธ ํผ์ด๊ฐ ์ฌ๊ฐํ ์์์ ๊ฐ์ง๊ณ ์์ง ์์ ๋์๋ง ์ ํฉํ ์์ ์ด๋ค. ์ด์ ํด๋นํ์ง ์์ผ๋ฉด, ์์ ์ค๋ช ํ close ๋ฉ์๋๋ฅผ ์ฌ์ฉํ๋ค.
์์ดํ
9. try-finally๋ณด๋ค๋ try-with-resources๋ฅผ ์ฌ์ฉํ๋ผ
ยท ์๋ฐ ๋ผ์ด๋ธ๋ฌ์ด์๋ close ๋ฉ์๋๋ฅผ ํธ์ถํด ์ง์ ๋ซ์์ค์ผ ํ๋ ์์์ด ๋ง๋ค.
ex) InputStream, OutputStream, java.sql.Connection
ยท ์์ ๋ซ๊ธฐ๋ ํด๋ผ์ด์ธํธ๊ฐ ๋์น๊ธฐ ์ฌ์์ ์์ธกํ ์ ์๋ ์ฑ๋ฅ ๋ฌธ์ ๋ก ์ด์ด์ง๊ธฐ๋ ํ๋ค.
- ์ด๋ฐ ์์ ์ค ์๋น์๋ ์์ ๋ง์ผ๋ก finalizer๋ฅผ ํ์ฉํ์ง๋ง, finalizer๋ ๋ฏฟ์์งํ์ง ๋ชปํ๋ค.
ยท ์ ํต์ ์ผ๋ก ์์์ ๋ซ๋ ์๋จ์ผ๋ก try-finally๊ฐ ์ฐ์์ง๋ง, ์์์ด ๋ ์ด์์ด๋ฉด ์ฝ๋๊ฐ ๋๋ฌด ์ง์ ๋ถํด์ง๋ค.
// ์์ ํ๋ ํ์
static String firstLineOfFile(String path) throws IOException {
BufferedReader br = new BufferedReader(new FileReader(path));
try {
return br.readLine();
} finally {
br.close();
}
}
// ์์ ๋ณต์๊ฐ ํ์
static void copy(String src, String dst) throws IOException {
InputStream in = new FileInputStream(src);
try {
OutputStream out = new FileOutputStream(dst);
try {
byte[] buf = new byte[BUFFER_SIZE];
int n;
while ((n = in.read(buf)) >= 0) {
out.write(buf, 0, n);
}
} finally {
out.close();
}
} finally {
in.close();
}
}
- ์ฌ์ง์ด ์์ ์ฝ๋ ๋ํ ๋ฏธ๋ฌํ ๊ฒฐ์ ์ด ์๋ค.
๋๋ณด๊ธฐ
ยท ์๋ฐ7์์ ๋ฑ์ฅํ try-with-resources์ try-finally์ ๊ฒฐ์ ์ ํด๊ฒฐํ๋ค.
- ์ด ๊ตฌ์กฐ๋ฅผ ์ฌ์ฉํ๋ ค๋ฉด ํ๋น ์์์ด AutoCloseable ์ธํฐํ์ด์ค๋ฅผ ๊ตฌํํด์ผ ํ๋ค.
- ๋จ์ํ void๋ฅผ ๋ฐํํ๋ close ๋ฉ์๋ ํ๋๋ง ์ ์ํ ์ธํฐํ์ด์ค๋ค.
ยท ๋ค์์ ์์ ์ฝ๋๋ฅผ try-with-resources๋ฅผ ์ฌ์ฉํด ์ฌ์์ฑํ ์ฝ๋๋ค.
static String firstLineOfFile(String path) throws IOException {
try (BufferedReader br = new BufferedReader(new FileReader(path))) {
return br.readLine();
}
}
static void copy(String src, String dst) throws IOException {
try (InputStream in = new FileInputStream(src);
OutputStream out = new FileOutputStream(dst)) {
byte[] buf = new byte[BUFFER_SIZE];
int n;
while ((n = in.read(buf)) >= 0) {
out.write(buf, 0, n);
}
}
}
ยท ์์ ์ฝ๋์์ ํ์ธํ ์ ์๋ฏ์ด try-with-resources ๋ฒ์ ์ด ์งง๊ณ ์ฝ๊ธฐ ์์ํ๋ฉฐ, ๋ฌธ์ ๋ฅผ ์ง๋จํ๊ธฐ๋ ํจ์ฌ ์ข๋ค.
- firstLineOfFile ๋ฉ์๋๋ฅผ ์ดํด๋ณด์. readLine๊ณผ (์ฝ๋์๋ ๋ํ๋์ง ์๋)close ํธ์ถ ์์ชฝ์์ ์์ธ๊ฐ ๋ฐ์ํ๋ฉด, close์์ ๋ฐ์ํ ์์ธ๋ ์จ๊ฒจ์ง๊ณ readLine์์ ๋ฐ์ํ ์์ธ๊ฐ ๊ธฐ๋ก๋๋ค.
- ์ด๋ ๊ฒ ์จ๊ฒจ์ง ์์ธ๋ค๋ ์คํ ์ถ์ ๋ด์ญ์ '์จ๊ฒจ์ก๋ค(suppressed)'๋ ๊ผฌ๋ฆฌํ๋ฅผ ๋ฌ๊ณ ์ถ๋ ฅ๋๋ค.
- ์๋ฐ 7์์ Throwable์ ์ถ๊ฐ๋ getSuppressed ๋ฉ์๋๋ฅผ ์ด์ฉํ๋ฉด ํ๋ก๊ทธ๋จ ์ฝ๋์์ ๊ฐ์ ธ์ฌ ์๋ ์๋ค.
ยท try-with-resources๋ catch ์ ์ ์ธ ์ ์๋ค.
- ์ด๋ฅผ ํตํด try ๋ฌธ์ ๋ ์ค์ฒฉํ์ง ์๊ณ ๋ค์์ ์์ธ๋ฅผ ์ฒ๋ฆฌํ ์ ์๋ค.
static String firstLineOfFile(String path, String defaultVal) {
try (BufferedReader br = new BufferedReader(new FileReader(path))) {
return br.readLine();
} catch (IOException e) {
return defaultVal;
}
}
Last updated