Data Scientist 옌

매일 발전하는 IT문제해결사

국비지원교육 (22.01-22.07)/강의노트

22-02-15(화) 014일차 [Java] 생성자, 상속, 메서드 오버라이딩

옌炎 2022. 4. 16. 14:55
728x90

수업내용


1교시 (09:30-10:20)

  • 지난 시간 복습
    • [PPT 32p] 생성자
      • new 키워드를 사용
      • 어떤 클래스에 대한 오브젝트를 생성할 때 자동적으로 호출되어 실행
      • 오브젝트 생성 시 한 번만 수행
      • 멤버 변수의 초기화

2교시 (10:30-11:20)

  • Exam_Const_1
package a.b.c.ch2;

public class Exam_Const_1 {

	String s;
	int i;

	// 프로그래머가 기본 생성자를 소스 코드에 작성했다.
	public Exam_Const_1() {
		System.out.println("Exam_Const_1() 생성자 >>> : ");
		System.out.println("Exam_Const_1() 생성자 >>> s ::: " + s);
		System.out.println("Exam_Const_1() 생성자 >>> i ::: " + i);
	}

	public static void main(String args[]) {
	
		/*
			1. Exam_Const_1 : 사용자정의 클래스 Exam_Const_1 를 사용하기 위해서 선언 했다.
			2. ec	: 선언한 Exam_Const_1 클래스를 사용하기 위해서 참조변수 ec 를 선언 했다.
			3. =	: 대입 연산자
			4. new	: 뉴 키워드, 뉴 인스턴스연산자, 뉴 연산자 
					: new 키워드 뒤에오는 생성자 = 클래스이름 + () 메모리에 올려주세요 
					: 메모리에 올리는 것은 자바 버철머신이다.
			5. Exam_Const_1()	:	생성자 이다. 
								:	인스턴스하는 클래스의 멤버변수를 초기화 한다.
								:	default value 또는 생상자의 인수로 있는 변수 값으로 초기화 한다.
			6. Exam_Const_1() 생성자는 Exam_Const_1 소스 코드에서 작성된
				public Exam_Const_1() {} 기본 생성자를 호출한다.
				멤버 필드에 선언된 String s, int i 를 default value 로 초기화 한다.
		*/
		Exam_Const_1 ec = new Exam_Const_1();

	}
}

3교시 (11:30-12:20)

  • Exam_Const_1 (계속)
package a.b.c.ch2;

public class Exam_Const_1 {

	String s;
	int i;

	// 프로그래머가 기본 생성자를 소스 코드에 작성했다.
	public Exam_Const_1() {
		this("김영하", 22);
		System.out.println("Exam_Const_1() 생성자 >>> : ");
		System.out.println("Exam_Const_1() 생성자 >>> s ::: " + s);
		System.out.println("Exam_Const_1() 생성자 >>> i ::: " + i);
	}

	public Exam_Const_1(String s, int i) {
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> :");		
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> s :::" + s);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> i :::" + i);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> this.s ::: " + this.s);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> this.i ::: " + this.i);
		this.s = s;
		this.i = i;
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> this.s ::: " + this.s);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> this.i ::: " + this.i);
	}

	public static void main(String args[]) {
	
		/*
			1. Exam_Const_1 : 사용자정의 클래스 Exam_Const_1 를 사용하기 위해서 선언 했다.
			2. ec	: 선언한 Exam_Const_1 클래스를 사용하기 위해서 참조변수 ec 를 선언 했다.
			3. =	: 대입 연산자
			4. new	: 뉴 키워드, 뉴 인스턴스연산자, 뉴 연산자 
					: new 키워드 뒤에오는 생성자 = 클래스이름 + () 메모리에 올려주세요 
					: 메모리에 올리는 것은 자바 버철머신이다.
			5. Exam_Const_1()	:	생성자 이다. 
								:	인스턴스하는 클래스의 멤버변수를 초기화 한다.
								:	default value 또는 생상자의 인수로 있는 변수 값으로 초기화 한다.
			6. Exam_Const_1() 생성자는 Exam_Const_1 소스 코드에서 작성된
				public Exam_Const_1() {} 기본 생성자를 호출한다.
				멤버 필드에 선언된 String s, int i 를 default value 로 초기화 한다.
		*/
		Exam_Const_1 ec = new Exam_Const_1();

		// 소스 코드 상에서 매개변수가 2개 있는 생성자를 호출한다.
		// public Exam_Const_1(String s, int i) {} 생성자를 호출한다.
		Exam_Const_1 ec_1 = new Exam_Const_1("홍길동", 26);

	}
}
  • Exam_Const_1 (계속) - this 키워드 설명
package a.b.c.ch2;

/*
	this   디스 키워드
		   자기 자신 클래스를 가리킨다.
		   this.getClass().getName();
	this() 디스 함수
		   자기 클래스에서 오버로딩된 생성자를 가리킬 때 (호출할 때) 사용한다.
*/

public class Exam_Const_1 {

	String s;
	int i;

	// 프로그래머가 기본 생성자를 소스코드에 작성했다.
	public Exam_Const_1() {
		// this("국민", 22);
		System.out.println("Exam_Const_1() 생성자 >>> ");
		System.out.println("Exam_Const_1() 생성자 >>> ::: " + s);
		System.out.println("Exam_Const_1() 생성자 >>> ::: " + i);
	}

	public Exam_Const_1(String s, int i) {
		/*
			this() : 디스 함수는 생성자 블록 안에서 꼭 첫 번째 문장으로 수행되어야 한다.
					 디스 함수는 생성자 블록 안에서 사용한다.
					 클래스 내부에 오버로드되어 overload 선언된 생성자를 호출한다.
			constructor overloading : 생성자의 시그니처 signature가 같고 매개변수가 다른 것
			함수의 시그니처		: 접근제한자 수정자 리턴형 함수이름
							   [public | protected | default | private]
							   [static | final]
							   [void | 데이터자료형]
							   함수이름
							   (매개변수)
			생성자 오버로딩 :
			함수 오버로딩 :
		*/

		this();
		// System.out.println("Exam_Const_1(string s, int i) 생성자 >>> : ");
		/*
		C:\00.KOSMO108\10.JExam\ch2>javac -d . Exam_Const_1.java
		Exam_Const_1.java:21: error: call to this must be first statement in constructor
						this();
							^
		1 error
		*/

		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> : ");
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> : s ::: " + s);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> : i ::: " + i);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> : this.s ::: " + this.s);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> : this.i ::: " + this.i);

		// 51-52 line과 60-61 line 출력이 같음
		// 그냥 s, i라 써도 JVM은 알아보나 프로그래머가 알아보기 위해서 this.s = s;라고 기재
		this.s = s;
		this.i = i;
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> : this.s ::: " + this.s);
		System.out.println("Exam_Const_1(String s, int i) 생성자 >>> : this.i ::: " + this.i);
	}

	// 매개변수가 2개 있는 생성자
	public static void main(String args[]) {
		
		/*
			1. Exam_Const_1 : 사용자 정의 클래스 Exam_Const_1을 사용하기 위해서 선언했다.
			2. ec			: 선언한 Exam_Const_1 클래스를 사용하기 위해서 참조변수 ec를 선언했다.
			3. =			: 대입 연산자
			4. new			: new 키워드, new 인스턴스 연산자, new 연산자
							: new 키워드 뒤에 오는 생성자 = 클래스이름 + () 메모리에 올려주세요
							: 메모리에 올리는 것은 자바 버추얼 머신이다.
			5. Exam_Const_1() : 생성자이다.
							: 인스턴스하는 클래스의 멤버 변수를 초기화한다.
							: default value 또는 생성자의 인수로 있는 변수 값으로 초기화한ㄴ다.
			6. Exam_Const_1() 생성자는 Exam_Const_1 소스 코드에서 작성된
				public Exam_Const_1() {] 기본 생성자를 호출한다.
				멤버 필드에서 선언된 String s, int i를 default value로 초기화한다.
		*/
		Exam_Const_1 ec = new Exam_Const_1();

		// 소스 코드 상에서 매개변수가 2개 있는 생성자를 호출한다.
		// public Exam_Const_1(String s, int i) {} 생성자를 호출한다.
		Exam_Const_1 ec_1 = new Exam_Const_1("홍길동", 26);

	}
}

4교시 (12:30-13:20)

  • Exam_Const_2
package a.b.c.ch2;

class Exam_ConstVO{

	private String mid;
	private String mpw;
	private String mname;
	private int mage;

	public Exam_ConstVO(){
		System.out.println("Exam_ConstVO() >>> this ::: " + this);		
		System.out.println("Exam_ConstVO() >>> :"
													+ this.getClass().getName());
	}

	public Exam_ConstVO(String mid, String mpw, String mname, int mage){
		System.out.println("Exam_ConstVO(String mid ...) >>> this ::: " + this);		
		System.out.println("Exam_ConstVO(String mid ...) >>> : "
													+ this.getClass().getName());
		this.mid = mid;
		this.mpw = mpw;
		this.mname = mname;
		this.mage = mage;
	}

	// setter : 세터 메소드 : 세터 함수 : 값을 초기화하는 함수
	/*
		pricate String mid 변수를 setter 함수 만들기
		1. set
		2. 멤버 변수의 변수명에 첫 번째 글자를 대문자로 변경한다. : Mid
		3. set + Mid = setMid()
		4. public void setMid(String mid) {this.mid = mid;}
	*/

	public void setMid(String mid) {
		this.mid = mid;
	}
	public void setMpw(String mpw) {
		this.mpw = mpw;
	}
	public void setMname(String mname) {
		this.mname = mname;
	}
	public void setMage(int mage) {
		this.mage = mage;
	}

	// getter : 게터 메소드 : 게터 함수 : 값을 리턴하는 함수
	/*
		private String mid 변수를 getter 함수 만들기
		1. get
		2. 멤버변수의 변수명에 첫 번째 글자를 대문자로 변경한다. : Mid
		3. get + Mid = getMid()
		4. public String getMid() {return this.mid;}
	*/

	public String getMid() {
		return this.mid;
	}
	public String getMpw() {
		return this.mpw;
	}
	public String getMname() {
		return this.mname;
	}
	public int getMage() {
		return this.mage;
	}
}

// Exam_Const_2 클래스에서 Exam_ConstVO의 private 변수를 불러오기 위한 함수인 get()와 set() 메소드 활용
public class Exam_Const_2 {
	
	public static void main(String args[]) {

		Exam_ConstVO ecvo = new Exam_ConstVO("SJH", "SJH00", "홍길동1", 27);
		System.out.println("echo 참조변수 주소값 >>> : " + ecvo);
		System.out.println("echo.getMid() >>> : " + ecvo.getMid() + "\n");

		Exam_ConstVO ecvo_1 = new Exam_ConstVO();
		System.out.println("ecvo_1 참조변수 주소값 >>> : " + ecvo_1);
		ecvo_1.setMid("HGD");
		ecvo_1.setMpw("HGD00");
		ecvo_1.setMname("홍길동");
		ecvo_1.setMage(23);
		System.out.println("ecvo_1.getMid() >>> : " + ecvo_1.getMid() + "\n");

		for (int i=0; i < 10; i++) {
			Exam_ConstVO ecvo_2 = new Exam_ConstVO();
			System.out.print("ecvo_2 참조변수 주소값 >>> : " + ecvo_2 + "\n");
			ecvo_2.setMid("HGD_" + i);
			ecvo_2.setMpw("HGD00_" + i);
			ecvo_2.setMname("홍길동_" + i);
			ecvo_2.setMage(23 + i);
			System.out.print(ecvo_2.getMid() + " : ");
			System.out.print(ecvo_2.getMpw() + " : ");
			System.out.print(ecvo_2.getMname() + " : ");
			System.out.println(ecvo_2.getMage() + " : ");
		}
	}
}
  • [교재 153~172p] 생성자 ~ this

5교시 (14:30-15:20)

  • Exam_Const_2 (계속)
package a.b.c.ch2;

class Exam_ConstVO{

	private String mid;
	private String mpw;
	private String mname;
	private int mage;

	public Exam_ConstVO(){
		System.out.println("Exam_ConstVO() >>> this ::: " + this);		
		System.out.println("Exam_ConstVO() >>> :"
													+ this.getClass().getName());
	}

	public Exam_ConstVO(String mid, String mpw, String mname, int mage){
		System.out.println("Exam_ConstVO(String mid ...) >>> this ::: " + this);		
		System.out.println("Exam_ConstVO(String mid ...) >>> : "
													+ this.getClass().getName());
		this.mid = mid;
		this.mpw = mpw;
		this.mname = mname;
		this.mage = mage;
	}

	// setter : 세터 메소드 : 세터 함수 : 값을 초기화하는 함수
	/*
		pricate String mid 변수를 setter 함수 만들기
		1. set
		2. 멤버 변수의 변수명에 첫 번째 글자를 대문자로 변경한다. : Mid
		3. set + Mid = setMid()
		4. public void setMid(String mid) {this.mid = mid;}
	*/

	public void setMid(String mid) {
		this.mid = mid;
	}
	public void setMpw(String mpw) {
		this.mpw = mpw;
	}
	public void setMname(String mname) {
		this.mname = mname;
	}
	public void setMage(int mage) {
		this.mage = mage;
	}

	// getter : 게터 메소드 : 게터 함수 : 값을 리턴하는 함수
	/*
		private String mid 변수를 getter 함수 만들기
		1. get
		2. 멤버변수의 변수명에 첫 번째 글자를 대문자로 변경한다. : Mid
		3. get + Mid = getMid()
		4. public String getMid() {return this.mid;}
	*/

	public String getMid() {
		return this.mid;
	}
	public String getMpw() {
		return this.mpw;
	}
	public String getMname() {
		return this.mname;
	}
	public int getMage() {
		return this.mage;
	}
}

// Exam_Const_2 클래스에서 Exam_ConstVO의 private 변수를 불러오기 위한 함수인 get()와 set() 메소드 활용
public class Exam_Const_2 {
	
	public static void main(String args[]) {

		Exam_ConstVO ecvo = new Exam_ConstVO("SJH", "SJH00", "홍길동", 27);
		System.out.println("echo 참조변수 주소값 >>> : " + ecvo);
		System.out.println("echo.getMid() >>> : " + ecvo.getMid() + "\n");

		Exam_ConstVO ecvo_1 = new Exam_ConstVO();
		System.out.println("ecvo_1 참조변수 주소값 >>> : " + ecvo_1);
		ecvo_1.setMid("HSA");
		ecvo_1.setMpw("HSA00");
		ecvo_1.setMname("홍길동1");
		ecvo_1.setMage(23);
		System.out.println("ecvo_1.getMid() >>> : " + ecvo_1.getMid() + "\n");

		for (int i=0; i < 10; i++) {
			Exam_ConstVO ecvo_2 = new Exam_ConstVO();
			System.out.print("ecvo_2 참조변수 주소값 >>> : " + ecvo_2 + "\n");
			ecvo_2.setMid("HGD_" + i);
			ecvo_2.setMpw("HGD00_" + i);
			ecvo_2.setMname("홍길동_" + i);
			ecvo_2.setMage(23 + i);
			System.out.print(ecvo_2.getMid() + " : ");
			System.out.print(ecvo_2.getMpw() + " : ");
			System.out.print(ecvo_2.getMname() + " : ");
			System.out.println(ecvo_2.getMage() + " : ");
		}
	}
}
  • 질문(참조변수의 값은 ecvo_2의 마지막 값인 인덱스 2?)과 답변
  • Exam_Const_2.java
  • [교재 231~347p] 자바의 핵심!
  • 상속
상속 inheritance : 클래스의 자원을 사용하기 위해서 : 자원 = 변수 + 함수
-----------------------
자바에서 상속은 클래스 상속이다.
자바 프로그램의 최소 단위는 클래스이다.

자바 클래스는 single inheritance : 단일 상속 : extends
자바 클래스에서 인터페이스 클래스는 multi inheritance : 다중 상속 : implements

클래스 = 변수 + 함수();

클래스의 종류
	일반 클래스				extends 키워드 사용해서 단일 상속
							변수 + 블록이 있는 함수() {}
							public class 사용자정의클래스이름 {
								public String s;
								public String aM() {
									return "aM() 함수";
								}
							}
	추상 클래스				extends 키워드 사용해서 단일 상속
							변수 + 블록이 있는 함수() {} + 블록이 없는 함수();
							public abstract class 사용자정의클래스이름 {
								public String s;
								public String aM() {
									return "aM 함수";
								}
								public abstract String bM(); <-- 추상함수: 함수에 {} 블록이 없는 함수
							}
	인터페이스 클래스			implements 키워드 사용해서 다중 상속
							단: 다중 상속은 인터페이스를 클래스에 상속할 때 적용
								인터페이스에서 인터페이스를 상속할 때는 extends 키워드 사용
							변수 + 블록이 없는 함수();
							public interface 사용자정의인터페이스클래스이름 {
								public interface final String S;
								public String ss;
								public abstract String aM(); <-- 추상함수: 함수에 {} 블록이 없는 함수
								public String bM(); <-- 추상함수: 함수에 {} 블록이 없는 함수
							}

자바 클래스의 발전 단계
일반 클래스 --> 추상 클래스 --> 인터페이스 클래스

6교시 (15:30-16:20)

  • 상속
package a.b.c.ch2;

class A_4 extends java.lang.Object {
	
	// 생성자
	A_4() {
		System.out.println("A_4() 생성자 >>> : ");
	}

	void a_4() {
		System.out.println("A_4().a_4() 함수 >>> : ");
	}
}

class A_3 extends A_4 {
	
	// 생성자
	A_3() {
		System.out.println("A_3() 생성자 >>> : ");
	}

	void a_3() {
		System.out.println("A_3().a_3() 함수 >>> : ");
	}
}

class A_2 extends A_3 {
	
	// 생성자
	A_2() {
		System.out.println("A_2() 생성자 >>> : ");
	}

	void a_2() {
		System.out.println("A_2().a_2() 함수 >>> : ");
	}
}

// A_2 부모 클래스, A_1 자식 클래스
class A_1 extends A_2 {
	
	// 생성자
	A_1() {
		System.out.println("A_1() 생성자 >>> : ");
	}

	void a_1() {
		System.out.println("A_1().a_1() 함수 >>> : ");
	}
}


public class Exam_Inheritance {

	public static void main(String args[]) {

		Exam_Inheritance ei = new Exam_Inheritance();
		System.out.println("ei 참조변수 주소값 >>> : " + ei);
		// ei.a_1();
		/*
			C:\00.KOSMO108\10.JExam\ch2>javac -d . Exam_Inheritance.java
			Exam_Inheritance.java:35: error: cannot find symbol
							ei.a_1();
							  ^
			  symbol:   method a_1()
			  location: variable ei of type
		*/		

		/*
			1.	A_1 클래스를 사용하려고 클래스를 선언한다.
			2. 참조변수 a1을 선언한다.
			3. = 대입 연산자
			4. new 연산자를 보고 jvm 생성자 A_1()을 찾아서
			   해당 객체를 메모리에 올리고 A_1() 생성자는 멤버변수를 초기화한다.
			5. A_1() 객체를 찾아서 메모리에 올리려고 하는데 A_2 클래스를 상속하고 있다.
			   class A_1 extends A_2
			6. jvm은 A_1() 클래스 그냥 두고 A_2() 클래스를 메모리에 올리려고 하는데
			   A_3 클래스를 상속하고 있다.
			   class A_2 extends A_3
			7. jvm은 A_2() 클래스 그냥 두고 A_3() 클래스를 메모리에 올리려고 하는데
			   A_4 클래스를 상속하고 있다.
			   class A_3 extends A_4
			8. jvm은 A_4 클래스를 찾아서 Default로 상속하고 있는 java.lang.Object 클래스를 메모리에 올리고
			9. A_4 클래스를 찾아서 메모리에 올리고 순차적으로 상속당한 클래스를 메모리에 올린다.\
		*/
		A_1 a1 = new A_1();
		System.out.println("a1 참조변수 주소값 >>> : " + a1);
		a1.a_1();
		a1.a_2();
		a1.a_3();
		a1.a_4();
	}
}

7교시 (16:30-17:20)

  • Exam_Inherit_1
package a.b.c.ch2;

import a.b.c.ch2.aa.Class_A;

public class Exam_Inherit_1 extends Class_A {

	public void class_a_1() {
		// System.out.println(""Class_A().class_a_1() 함수 >>> : ");
		System.out.println("Exam_Inherit_1().class_a_1() 함수 >>> : ");
	}

	public static void main(String args[]) {
	
		Exam_Inherit_1 ei1 = new Exam_Inherit_1();
		System.out.println("ei1 참조변수 주소값 >>> : " + ei1);
		System.out.println("ei1.getClass().getName() >>> : " + ei1.getClass().getName());

		ei1.class_a_1();
	}
}

// C:\00.KOSMO108\10.JExam\ch2>javac -d . Exam_Inherit_1.java Class_A.java
// C:\00.KOSMO108\10.JExam\ch2>java a.b.c.ch2.Exam_Inherit_1
  • Class_A
package a.b.c.ch2.aa;

public class Class_A extendds java.lang.Object {

	// 생성자 2개
	public Class_A() {
		System.out.prontln("Class_A() 생성자 >>> : ");
	}

	public Class_A(String s) {
		System.out.println("Class_A(String s) 생성자 >>> : " + s);
	} 

	// 함수 2개
	public void class_a_1() {
		System.out.println("Class_A().class_a_1() 함수 >>> : ");
	}

	public String class_a_2() {
		System.out.println("Class_A().class_a_2() 함수 >>> : ");
		
		return "class_a_2() 함수 >>> : ";
	}
}

8교시 (17:30-18:30)

  • [교재 252p] 메서드 오버라이딩
    • 상위 클래스에 정의한 메서드가 하위 클래스에서 구현할 내용과 맞지 않을 경우 하위 클래스에서 이 메서드를 재정의
  • Class_A (계속)
package a.b.c.ch2.aa;

public class Class_A extends java.lang.Object {

	// 생성자 2개
	public Class_A() {
		System.out.println("Class_A() 생성자 >>> : ");
	}

	public Class_A(String s) {
		System.out.println("Class_A(String s) 생성자 >>> : " + s);
	} 

	// 함수 2개
	public void class_a_1() {
		System.out.println("Class_A().class_a_1() 함수 >>> : ");
	}

	public String class_a_2() {
		System.out.println("Class_A().class_a_2() 함수 >>> : ");
		
		return "class_a_2() 함수 >>> : ";
	}

	/*
		java.lang.Object
		public String toString() {
		    return getClass().getName() + "@" + Integer.toHexString(hashCode());
		}
	*/
	/*
		@Override
		public String toString(){
			return "Class_A().toString() 함수 >>> : ";
		}
	*/
}
  • Exam_Inherit_1 (계속)
package a.b.c.ch2;

import a.b.c.ch2.aa.Class_A;

public class Exam_Inherit_1 extends Class_A {

	/*
		public String toString(){
			return "Class_A().toString() 함수 >>> : ";
		}
	*/

	@Override
	public String toString() {
		return "Exam_Inherit_1().toString() 함수 >>> : ";
	}

	// 어노테이션 Annotation
	@Override
	public void class_a_1() {
		// System.out.println(""Class_A().class_a_1() 함수 >>> : ");
		System.out.println("Exam_Inherit_1().class_a_1() 함수 >>> : ");
	}

	public static void main(String args[]) {
	
		Exam_Inherit_1 ei1 = new Exam_Inherit_1();
		System.out.println("ei1 참조변수 주소값 >>> : " + ei1);
		System.out.println("ei1.getClass().getName() >>> : " + ei1.getClass().getName());

		ei1.class_a_1();
	}
}

// C:\00.KOSMO108\10.JExam\ch2>javac -d . Exam_Inherit_1.java Class_A.java
// C:\00.KOSMO108\10.JExam\ch2>java a.b.c.ch2.Exam_Inherit_1

Notes

  • 다형성은 어려워서 배우지 않고 사용법만 배움

728x90