item 24 Jung inchul - JAVA-JIKIMI/EFFECTIVE-JAVA3 GitHub Wiki
Effective Java 3e ์์ดํ 24๋ฅผ ์์ฝํ ๋ด์ฉ ์ ๋๋ค.
์ค์ฒฉ ํด๋์ค
๋ ์์ ์ ๊ฐ์ผ ๋ฐ๊นฅ ํด๋์ค์์๋ง ์ฐ์ฌ์ผ ํ๋ฉฐ, ๊ทธ ์ธ์ ์ฐ์์๊ฐ ์๋ค๋ฉด ํฑ๋ ๋ฒจ ํด๋์ค
๋ก ๋ง๋ค์ด์ผ ํ๋ค. ์ค์ฒฉ ํด๋์ค์ ์ข
๋ฅ๋ ์ ์ ๋ฉค๋ฒ ํด๋์ค
, (๋น์ ์ ) ๋ฉค๋ฒ ํด๋์ค
, ์ต๋ช
ํด๋์ค
, ์ง์ญ ํด๋์ค
์ด๋ ๊ฒ ๋ค ๊ฐ์ง๋ค.
์ ์ ๋ฉค๋ฒ ํด๋์ค๋ ๋ค๋ฅธ ํด๋์ค ์์ ์ ์ธ๋๊ณ , ๋ฐ๊นฅ ํด๋์ค์ private
๋ฉค๋ฒ์๋ ์ ๊ทผํ ์ ์๋ค๋ ์ ๋ง ์ ์ธํ๊ณ ๋ ์ผ๋ฐ ํด๋์ค
์ ๋๊ฐ๋ค. ์ ์ ๋ฉค๋ฒ ํด๋์ค๋ ํํ ๋ฐ๊นฅ ํด๋์ค์ ํจ๊ป
์ฐ์ผ ๋๋ง ์ ์ฉํ private ๋์ฐ๋ฏธ ํด๋์ค๋ก ์ฐ์ธ๋ค.
public class StaticCar {
static String _where="I am a Car from Germany!";
Country _country; // object of inner class country
StaticCar(){
_country=new Country(); // instantiate the inner class
}
static class Country { // static member inner class
String showCountry() {
return _where;
}
}
public static void main(String[] args) {
StaticCar myCar= new StaticCar() ; // instantiated object of class StaticCar
System.out.print("Access through an Country reference");
System.out.println(" created in an object of a StaticCar:");
System.out.println(myCar._country.showCountry());
// instantiated object of class StaticCar.Country
StaticCar.Country country= new StaticCar.Country();
System.out.println("Access through an Country reference that is local:");
System.out.println(country.showCountry());
}
}
Access through an Country reference created in an object of a StaticCar:
I am from Germany!
Access through an Country reference that is local:
I am from Germany!
์ ์
๋ฉค๋ฒ ํด๋์ค์ ๋น์ ์
๋ฉค๋ฒ ํด๋์ค์ ๊ตฌ๋ฌธ์ ์ฐจ์ด๋ ๋จ์ง static
์ด ๋ถ์ด ์๊ณ ์๊ณ ๋ฟ์ด์ง๋ง, ์๋ฏธ์ ์ฐจ์ด๋ ์ด์ธ๋ก ๊ฝค ํฌ๋ค. ๋น์ ์ ๋ฉค๋ฒ ํด๋์ค์ ์ธ์คํด์ค๋ ๋ฐ๊นฅ ํด๋์ค์ ์ธ์คํด์ค์ ์๋ฌต์
์ผ๋ก ์ฐ๊ฒฐ๋๋ค. ๊ทธ๋์ ๋น์ ์ ๋ฉค๋ฒ ํด๋์ค์ ์ธ์คํด์ค ๋ฉ์๋์์ ์ ๊ทํ๋ this
๋ฅผ ์ฌ์ฉํด ๋ฐ๊นฅ ์ธ์คํด์ค์ ๋ฉ์๋๋ฅผ ํธ์ถํ๊ฑฐ๋ ๋ฐ๊นฅ ์ธ์คํด์ค์ ์ฐธ์กฐ
๋ฅผ ๊ฐ์ ธ์ฌ ์ ์๋ค. ์ ๊ทํ๋ this๋ ํด๋์ค๋ช
.this
ํํ๋ก ๋ฐ๊นฅ ํด๋์ค์ ์ด๋ฆ์ ๋ช
์ํ๋ ์ฉ๋ฒ์ ๋งํ๋ค.
๋น์ ์ ๋ฉค๋ฒ ํด๋์ค์ ์ธ์คํด์ค์ ๋ฐ๊นฅ ์ธ์คํด์ค ์ฌ์ด์ ๊ด๊ณ๋ ๋ฉค๋ฒ ํด๋์ค๊ฐ ์ธ์คํด์คํ
๋ ๋ ํ๋ฆฝ ๋๋ฉฐ, ๋ ์ด์ ๋ณ๊ฒฝํ ์ ์๋ค.
๋น์ ์ ๋ฉค๋ฒ ํด๋์ค๋ ์ด๋ํฐ
๋ฅผ ์ ์ํ ๋ ์์ฃผ ์ฐ์ธ๋ค. ์ฆ, ์ด๋ค ํด๋์ค์ ์ธ์คํด์ค๋ฅผ ๊ฐ์ธ ๋ง์น ๋ค๋ฅธ ํด๋์ค์ ์ธ์คํด์ค์ฒ๋ผ ๋ณด์ด๊ฒ ํ๋ ๋ทฐ๋ก ์ฌ์ฉํ๋ ๊ฒ์ด๋ค. ๋น์ทํ๊ฒ, Set
๊ณผ List
๊ฐ์ ๋ค๋ฅธ ์ปฌ๋ ์
์ธํฐํ์ด์ค ๊ตฌํ ๋ค๋ ์์ ์ ๋ฐ๋ณต์๋ฅผ ๊ตฌํํ ๋ ๋น์ ์ ๋ฉค๋ฒ ํด๋์ค๋ฅผ ์ฃผ๋ก ์ฌ์ฉํ๋ค.
public class MySet<E> extends AbstractSet<E> {
... // ์๋ต
@Override public Iterator<E> iterator() {
return new MyIterator();
}
private class MyIterator implements Iterator<E> {
...
}
}
๋ฉค๋ฒ ํด๋์ค์์ ๋ฐ๊นฅ ์ธ์คํด์ค์ ์ ๊ทผํ ์ผ์ด ์๋ค๋ฉด ๋ฌด์กฐ๊ฑด static
์ ๋ถ์ฌ์ ์ ์ ๋ฉค๋ฒ ํด๋์ค๋ก ๋ง๋ค์. static
์ ์๋ตํ๋ฉด ๋ฐ๊นฅ ์ธ์คํด์ค๋ก์ ์จ์ ์ธ๋ถ ์ฐธ์กฐ
๋ฅผ ๊ฐ๊ฒ ๋๋ค. ๊ทธ๋ฌ๋ฉด ๊ฐ๋น์ง ์ปฌ๋ ์
์ด ๋ฐ๊นฅ ํด๋์ค์ ์ธ์คํด์ค๋ฅผ ์๊ฑฐํ์ง ๋ชปํ๋ ๋ฉ๋ชจ๋ฆฌ ๋์
๊ฐ ์๊ธธ ์ ์๋ค๋ ์ ์ด๋ค.
์ต๋ช
ํด๋์ค
๋ ๋ฐ๊นฅ ํด๋์ค์ ๋ฉค๋ฒ๋ ์๋๋ค. ๋ฉค๋ฒ์ ๋ฌ๋ฆฌ, ์ฐ์ด๋ ์์ ์ ์ ์ธ
๊ณผ ๋์์ ์ธ์คํด์ค
๊ฐ ๋ง๋ค์ด์ง๋ค. ๊ทธ๋ฆฌ๊ณ ์ค์ง ๋น์ ์ ์ธ ๋ฌธ๋งฅ
์์ ์ฌ์ฉ๋ ๋๋ง ๋ฐ๊นฅ ํด๋์ค์ ์ธ์คํด์ค๋ฅผ ์ฐธ์กฐํ ์ ์๋ค. ์ ์ ๋ฌธ๋งฅ
์์๋ผ๋ ์์ ๋ณ์ ์ด์ธ์ ์ ์ ๋ฉค๋ฒ๋ ๊ฐ์ง ์ ์๋ค. ์ฆ, ์์ ํํ
์ ์ํด ์ด๊ธฐํ ๋ final
๊ธฐ๋ณธ ํ์
๊ณผ ๋ฌธ์์ด ํ๋๋ง ๊ฐ์ง ์ ์๋ค.
interface Inter {
public void hi();
}
class Anony {
public void f() {
System.out.println("Anony.f() ํธ์ถ.");
}
}
public class Test {
private Integer number;
public void nonStaticMethod(){
Inter ob2 = new Inter() {
public void hi() {
System.out.println("๋น ์ ์ ๋ฌธ๋งฅ ๋ฉ์๋ ํธ์ถ" + number);
}
};
}
public static void staticMethod() {
Inter ob2 = new Inter() {
Integer number2 = 1;
public void hi() {
System.out.println("์ ์ ๋ฌธ๋งฅ ๋ฉ์๋ ํธ์ถ" + number); // comile Error
}
};
}
public static void main(String[] args) throws Exception {
//Inter ob1 = new Inter(); //Compile Error!!!
Inter ob2 = new Inter() {
public void hi() {
System.out.println("์๋
ํ์ญ๋๊น?");
}
};
ob2.hi();
Anony a1 = new Anony();
Anony a2 = new Anony() {
public void f() {
System.out.println("์ดํํ.");
}
};
a1.f();
a2.f();
}
}
์ ์ ๋ฌธ๋งฅ์์ final ๊ธฐ๋ณธ ํ์ ๊ณผ ๋ฌธ์์ด ํ๋๋ง ๊ฐ์ง ์ ์๋ค๋ ์๋ฏธ๋?
์ต๋ช
ํด๋์ค๋ฅผ ์ฌ์ฉํ๋ ํด๋ผ์ด์ธํธ๋ ๊ทธ ์ต๋ช
ํด๋์ค๊ฐ ์์ ํ์
์์ ์์ํ ๋ฉค๋ฒ ์ธ์๋ ํธ์ถํ ์ ์๋ค.
์ต๋ช
ํด๋์ค์ ๋ ๋ค๋ฅธ ์ฃผ์ฐ์์ ์ ์ ํฉํฐ๋ฆฌ ๋ฉ์๋
๋ฅผ ๊ตฌํํ ๋๋ค.
static List<Integer> intArrayAsList<int[] a) {
Objects.requireNonNulkl(a);
// ๋ค์ด์๋ชฌ๋ ์ฐ์ฐ์๋ฅผ ์ด๋ ๊ฒ ์ฌ์ฉํ๋ ๊ฑด ์๋ฐ 9๋ถํฐ ๊ฐ๋ฅํ๋ค.
// ๋ ๋ฎ์ ๋ฒ์ ์ ์ฌ์ฉํ๋ค๋ฉด <Integer>๋ก ์์ ํ์.
return new AbstractList<>() {
@Override public Integer get(int i) {
return a[i];
}
@Override public Integer set(int i, Integer val) {
int oldVal = a[i];
a[i] = val;
return oldVal;
}
@Override public int size() {
return a.length;
}
}
์ง์ญ ํด๋์ค
๋ ์ง์ญ ๋ณ์
๋ฅผ ์ ์ธํ ์ ์๋ ๊ณณ์ด๋ฉด ์ค์ง์ ์ผ๋ก ์ด๋์๋ ์ ์ธํ ์ ์๊ณ , ์ ํจ ๋ฒ์
๋ ์ง์ญ ๋ณ์์ ๊ฐ๋ค. ๋ฉค๋ฒ ํด๋์ค ์ฒ๋ผ ์ด๋ฆ์ด ์๊ณ ๋ฐ๋ณตํด์ ์ฌ์ฉํ ์ ์๋ค. ์ต๋ช
ํด๋์ค์ฒ๋ผ ๋น ์ ์ ๋ฌธ๋งฅ
์์ ์ฌ์ฉ๋ ๋๋ง ๋ฐ๊นฅ ์ธ์คํด์ค
๋ฅผ ์ฐธ์กฐํ ์ ์์ผ๋ฉฐ, ์ ์ ๋ฉค๋ฒ๋ ๊ฐ์ง ์ ์์ผ๋ฉฐ, ๊ฐ๋
์ฑ์ ์ํด ์งง๊ฒ ์์ฑํด์ผ ํ๋ค.
์ค์ฒฉ ํด๋์ค
์๋ ๋ค ๊ฐ์ง๊ฐ ์์ผ๋ฉฐ, ๊ฐ๊ฐ์ ์ฐ์์ด ๋ค๋ฅด๋ค. ๋ฉ์๋
๋ฐ์์๋ ์ฌ์ฉํด์ผ ํ๊ฑฐ๋ ๋ฉ์๋ ์์ ์ ์ํ๊ธฐ์ ๋๋ฌด ๊ธธ๋ค๋ฉด ๋ฉค๋ฒ ํด๋์ค
๋ก ๋ง๋ ๋ค. ๋ฉค๋ฒ ํด๋์ค์ ์ธ์คํด์ค ๊ฐ๊ฐ์ด ๋ฐ๊นฅ ์ธ์คํด์ค๋ฅผ ์ฐธ์กฐ
ํ๋ค๋ฉด ๋น ์ ์
์ผ๋ก, ๊ทธ๋ ์ง ์์ผ๋ฉด ์ ์
์ผ๋ก ๋ง๋ค์. ์ค์ฒฉ ํด๋์ค๊ฐ ํ ๋ฉ์๋ ์์์๋ง ์ฐ์ด๋ฉด์ ๊ทธ ์ธ์คํด์ค๋ฅผ ์์ฑํ๋ ์ง์
์ด ๋จ ํ ๊ณณ์ด๊ณ ํด๋น ํ์
์ผ๋ก ์ฐ๊ธฐ์ ์ ํฉํ ํด๋์ค๋ ์ธํฐํ์ด์ค๊ฐ ์ด๋ฏธ ์๋ค๋ฉด ์ต๋ช
ํด๋์ค
๋ก ๋ง๋ค๊ณ , ๊ทธ๋ ์ง ์์ผ๋ฉด ์ง์ญ ํด๋์ค
๋ก ๋ง๋ค์.