본문 바로가기
프로그래밍언어/Java

06-3. 생성자

by 스꼬맹이브로 2021. 2. 8.
728x90
반응형
SMALL

생성자(Constructor) : new 연산로 클래스로부터 객체를 생성할 때 호출되어 객체의 초기화를 담당

  객체 초기화 :  필드를 초기화하거나 메소드를 호출해서 객체를 사용할 준비를 하는 것

 

<기본 생성자>

  • 모든 클래스는 생성자가 반드시 존재함.
  • 생성자를 하나 이상 가질 수 있음.
  • 만약 생성자 선언을 생략했다면 기본 생성자를 생성함
//기본 생성자
[public] class() { }
  • 클래스가 public class로 선언되면 기본 생성자도 public 이지만, public 없이 class로만 선언되면 기본생성자에도 public이 붙지 않음

  • 그림과 같이 기본으로 생성자를 생성하기 때문에 new연산자 뒤에 기본 생성자를 호출해서 객체 생성 가능
  • 생성자가 한개 이상 선언이 된 경우 기본 생성자를 추가하지 않음

<생성자 선언>

//생성자 선언 방법
class(매개변수선언, ...){
//객체의 초기화 코드

}
  • 생성자는 메소드와 비슷한 모양을 가지고 있으나, 리턴 타입이 없고 클래스 이름과 동일
  • 생성자 블록 내부에 객체 초기화 코드 작성 (필드 초기값 저장, 메소드 호출 등)
  • 매개 변수 선언은 생략 가능하며 여러개 선언도 가능함.
  • 클래스에 생성자가 명시적으로 선언될 경우, 반드시 선언된 생성자를 호출해서 객체 생성해야 함

ex) Car클래스의 생성자로 객체 만들기

 

1. 생성자 선언

public class Car_2 {
	//생성자
	Car_2(String color, int cc) {
	}
}

2. 생성자 호출해서 객체 생성

public class CarExample_2 {
	public static void main(String[] args) {
		Car_2 myCar = new Car_2("검정", 3000);
		//Car myCar = new Car();  (x)
	}
}

 

<필드 초기화>

클래스로부터 객체가 생성될 때 필드는 기본 초기값으로 자동 설정됨.

다른 값으로 초기화 하려면 다음과 같은 방법이 있음.

1. 필드를 선언할 때 초기값 설정 → 동일한 클래스로부터 생성되는 객체들은 모두 같은 값을 가짐

ex) 대한민국 국적의 사람인 객체 생성

//필드 선언시 초기값 설정
public class Korean{
  String nation = "대한민국";
  String name;
  String ssn;
}

//선언
Korean k1 = new Korean();
Korean k2 = new Korean();

2. 생성자에서 초기값 설정 → 외부에서 제공되는 다양한 값들로 초기화할 때 사용

//필드 선언시 초기값 설정
public class Korean{
  String nation = "대한민국";
  String name;
  String ssn;

  //생성자
  public Korean(String n, String s){
  	name = n;
  	ssn = s;
  }
}
public class KoreanExample {
	public static void main(String[] args) {
		Korean k1 = new Korean("박자바", "011225-1234567");
		System.out.println("k1.name : " + k1.name);
		System.out.println("k1.ssn : " + k1.ssn);
		
		Korean k2 = new Korean("김자바", "930525-0654321");
		System.out.println("k2.name : " + k2.name);
		System.out.println("k2.ssn : " + k2.ssn);
	}
}

결과 :

*매개 변수의 이름이 너무 짧으면 코드의 가독성이 좋지 않기 때문에 가능한 초기화신킬 필드 이름과 비슷하거나 동일한 이름을 사용하는 것이 좋다.

하지만 위의 예제에서는 n과 s를 name, ssn으로 선언할 수 없다. 

그 이유는 필드와 매개 변수 이름이 동일하면 동일한 이름의 매개 변수가 사용 우선순위가 높기 때문에 생성자 내부에서 해당 필드에 접근할 수 없기 때문.

 

이름을 같이 쓰려면 필드 앞에 this.를 붙이기!

(this는 객체 자신의 참조인데 객체는 객체 자신을 this라고 하기 때문에 참조 변수로 필드를 사용하는 것과 동일)

//생성자
public Korean(String name, String ssn){
  this.name = name; //첫번째 name은 필드, 두번째 name은 매개변수 값
  this.ssn = ssn;   //첫번째 ssn은 필드, 두번째 ssn은 매개변수 값
}

 

<생성자 오버로딩>

생성자 오버로딩(overloading) : 매개 변수를 달리하는 생성자를 여러 개 선언하는 것.

public class Car {
  Car(){...}	//1번 생성자
  Car(String model){...}	//2번 생성자
  Car(String model, String color){...}		//3번 생성자
  Car(String model, String color, int max Speed){...}	//4번 생성자
}

<주의> 매개 변수의 타입과 개수 선언된 순서가 똑같을 경우, 매개 변수 이름만 바꾸는 것은 오버로딩이 아님.

Car(String model, String color){...}
Car(String color, String model){...}//오버로딩이 아님

생성자가 오버로딩되어 있을 경우, new 연산자로 생성자를 호출할 대 제공되는 매개값의 타입과 수에 의해 호출될 생성자 결정됨.

Car car1 = new Car();		//1번 생성자
Car car2 = new Car("그랜저");		//2번 생성자
Car car3 = new Car("그랜저","흰색");		//3번 생성자
Car car4 = new Car("그랜저","흰색",300);		//4번 생성자

ex)Car클래스에서 여러개 생성자 생성 후 사용

public class Car {
	//필드
	String company = "현대자동차";
	String model;
	String color;
	int maxSpeed;
	
	//생성자
	Car() {
	}
	
	Car(String model) {
		this.model = model;
	}
	
	Car(String model, String color) {
		this.model = model;
		this.color = color;
	}
	
	Car(String model, String color, int maxSpeed) {
		this.model = model;
		this.color = color;
		this.maxSpeed = maxSpeed;
	}
}
public class CarExample {
	public static void main(String[] args) {
		Car car1 = new Car();
		System.out.println("car1.company : " + car1.company);
		System.out.println();
		
		Car car2 = new Car("자가용");
		System.out.println("car2.company : " + car2.company);
		System.out.println("car2.model : " + car2.model);
		System.out.println();
		
		Car car3 = new Car("자가용", "빨강");
		System.out.println("car3.company : " + car3.company);
		System.out.println("car3.model : " + car3.model);
		System.out.println("car3.color : " + car3.color);
		System.out.println();
		
		Car car4 = new Car("택시", "검정", 200);
		System.out.println("car4.company : " + car4.company);
		System.out.println("car4.model : " + car4.model);
		System.out.println("car4.color : " + car4.color);
		System.out.println("car4.maxSpeed : " + car4.maxSpeed);
	}
}

 

결과:

<다른 생성자 호출 : this()>

생성자 오버로딩이 많아질 경우 중복 코드 발생↑

→ 필드 초기화 내용은 한 생성자에만 집중적으로 작성 후 나머지 생상자는 초기화 내용을 가지고 있는 생성자를 호출하는 방법으로 개선할 수 있음.

 

생성자에서 다른 생성자를 호출하는 방법

class([매개변수, ...]){
  this(매개변수, ..., 값, ...);
  실행문;
}

여기서 this는 자신의 다른 생성자를 호출하는 코드, 반드시 생성자의 첫 줄에서만 허용됨.

 

ex)사용 예시

변경 전.

Car(String model) {
  this.model = model;
  this.color = "은색";
  this.maxSpeed = 250;
}

Car(String model, String color) {
  this.model = model;
  this.color = color;
  this.maxSpeed = 250;
}

Car(String model, String color, int maxSpeed) {
  this.model = model;
  this.color = color;
  this.maxSpeed = maxSpeed;
}

 

변경 후.

public class Car {
	//필드
	String company = "현대자동차";
	String model;
	String color;
	int maxSpeed;
	
	//생성자
	Car() {
	}
	
	Car(String model) {
		this(model, null, 0);
	}
	
	Car(String model, String color) {
		this(model, color, 0);
	}
	
	Car(String model, String color, int maxSpeed) {
		this.model = model;
		this.color = color;
		this.maxSpeed = maxSpeed;
	}
}
public class CarExample {
	public static void main(String[] args) {
		Car car1 = new Car();
		System.out.println("car1.company : " + car1.company);
		System.out.println();
		
		Car car2 = new Car("자가용");
		System.out.println("car2.company : " + car2.company);
		System.out.println("car2.model : " + car2.model);
		System.out.println();
		
		Car car3 = new Car("자가용", "빨강");
		System.out.println("car3.company : " + car3.company);
		System.out.println("car3.model : " + car3.model);
		System.out.println("car3.color : " + car3.color);
		System.out.println();
		
		Car car4 = new Car("택시", "검정", 200);
		System.out.println("car4.company : " + car4.company);
		System.out.println("car4.model : " + car4.model);
		System.out.println("car4.color : " + car4.color);
		System.out.println("car4.maxSpeed : " + car4.maxSpeed);
	}
}

결과 :

728x90
반응형
LIST

'프로그래밍언어 > Java' 카테고리의 다른 글

06-5 인스턴스 멤버와 정적 멤버  (0) 2021.02.17
06-4 메소드  (0) 2021.02.15
06-2. 필드  (0) 2021.01.26
06-1. 객체 지향 프로그래밍  (1) 2021.01.25
05-3. 열거 타입  (0) 2021.01.24