자바 컴파일러는 메소드 이름, 매개변수 수, 매개변수 타입의 순서를 이용해 메소드를 구분한다. 때문에 이들을 메소드의 시그니처 라고 한다. (리턴 타입은 상관없음)
public class Signature {
public int myMethod(int x, int y) {
return 0;
}
public int myMethod(String x, int y) {
return 1;
}
public int myMethod(int x) {
return 1;
}
// 불가능
public String myMethod(int a, int b) {
return "1";
}
같은 이름의 메소드를 중복하여 정의하는 것을 의미, 서로 다른 시그니처를 가진 여러 메소드를 정의하는 것.
println 함수로 모든 타입을 출력할 수 있는 이유
생성자를 2개 이상 만드는 것. 매개변수를 다르게 선언하면 된다.
부모 클래스가 가지고 있는 메소드를 자식 클래스에서 재정의 해서 사용하는 것
자바는 객체들간의 메시지 전송(메서드를 호출) 을 기반으로 문제를 해결함, 이를 디스패치라고 한다. - 어떤 메서드를 호출할지 결정하여 실제로 실행시키는 과정
정적 디스패치와 동적 디스패치가 있는데, 정적은 컴파일 시점에 어떤 메소드가 호출될지 정해져 있는 것이고, 동적은 호출되는 메소드가 동적으로 정해지는 것
public class Parent {
public void work() {
System.out.println("parent work");
}
}
public class Child extends Parent{
@Override
public void work() {
System.out.println("child work");
}
}
public class App {
public static void main(String[] args) {
Child worker = new Child();
worker.work(); // 정적 메소드 디스패치
}
}
worker.work() 를 호출했을 때 Child 타입의 객체를 생성했기에 Child 클래스의 함수가 호출될 것을 알고 있다. 객체 생성은 Runtime 시에 호출된다. 컴파일 시점에는 타입에 대한 정보를 알 수 있다.
컴파일러는 Child 라는 타입을 명확히 알고 있다.
public class App {
public static void main(String[] args) {
Parent worker = new Child();
worker.work(); // 정적 메소드 디스패치
}
}
컴파일러가 Parent와 Child 중 어떤 메소드를 호출해야 되는지 모르고, 런타임시에 정해져서 메소드를 호출