본문 바로가기

IT코딩공부!

#10 형성 : day9 복습, 하나의 객체(info)에서 // 여러타입을 참조할 수 있는 방식을 제공해준다. (+추상클래스 + Util)

[0] day9복습

// 날짜여부 확인

Q. 우리가 입력한 년도,,일을 통해 해당하는 날짜가 존재하는지 유뮤 확인
ex) 2023. 04.03. >> 존재O
ex) 2023. 12.32. >> 존재X

// 필드

// 필드
    private  int year;   //년
    private  int month; //월
    private  int day;   //일
    private  boolean isValid = true; //존재여부(참으로 해둠)

// 생성자

// 생성자
	// 기본생성자
    public myDate() {

    }

	// 매개변수생성자
    public myDate(int year, int month, int day, boolean isValid) {
        this.year = year;
        this.month = month;
        this.day = day;
        this.isValid = isValid;
    }

// 메소드

// 메소드
// Alt + Insert 사용!!
    public int getYear() {
        return year;
    }

    public void setYear(int year) {
        // 년도 : 0보다 크거나 같음
        if(year >= 0){
            this.year = year;
        } else {
            isValid = false;
        }

    }

    public int getMonth() {
        return month;
    }

    public void setMonth(int month) {
        // 월 : 1 ~ 12월 사이 1<?<12
        if(month >= 1 && month <= 12){
            this.month = month;
        } else {
            isValid = false;
        }


    }

    public int getDay() {
        return day;
    }

    public void setDay(int day) {
        // 일
        // 1, 3, 5, 7, 8, 10, 12 >> 31일
        // 4, 6, 9, 11월 >> 30일
        // 2월 >> 28일 / 2월은 윤년
        // (1) 4년마다 한번씩 29일
        // (2) 100년마다 한번씩 28일
        // (3) 400년마다 한번씩 29일

        switch (month){
            case 1:
            case 3:
            case 5:
            case 7:
            case 8:
            case 10:
            case 12:
                if (day >=1 && day <=31) {
                    this.day = day;
                } else {
                    isValid = false;
                }
                break;
            case 4:
            case 6:
            case 9:
            case 11:
                if (day >=1 && day <=30) {
                    this.day = day;
                } else {
                    isValid = false;
                }
                break;
            case 2:
                if ((year % 4 == 0 && year%100 != 0) || year%400 ==0){
                    if (day >=1 && day <=29) {
                        this.day = day;
                    } else {
                        isValid = false;
                    }
                } else {
                    if (day >=1 && day <=28) {
                        this.day = day;
                    } else {
                        isValid = false;
                    }
                }
                break;
            default:
                isValid = false;
                break;
        }
    }

    public boolean isValid() {
        return isValid;
    }

    public void setValid(boolean valid) {
        isValid = valid;
    }


    // toString
    @Override
    public String toString() {
        return "myDate{" +
                "year=" + year +
                ", month=" + month +
                ", day=" + day +
                ", isValid=" + isValid +
                '}';
    }
}

// Main클래스에서 결과값 확인

import java.util.Scanner;

public class myDateMain {

    public static void main(String[] args) {

        Scanner sc = new Scanner(System.in);
        myDate mDate = new myDate();

        System.out.println("년도 입력 : ");
        mDate.setYear(sc.nextInt());
        System.out.println("월도 입력 : ");
        mDate.setMonth(sc.nextInt());
        System.out.println("일도 입력 : ");
        mDate.setDay(sc.nextInt());

        System.out.println(mDate);

        System.out.println("날짜 여부 확인");
        System.out.println( mDate.getYear() + "년 " + mDate.getMonth() + "월" + mDate.getDay() +"일");

        if (mDate.isValid()){
            System.out.println("존재하는 날짜");
        } else {
            System.out.println("존재하지 않은 날짜");
        }
    }
}

// 출력

조건에 맞는 경우
조건에 맞지 않는 경우


[1] 상속(Interitance) 개념

자바에서는 자식이 부모것을 물려 받는다

 

package Java0403;

public class _01_inheritance {
    /*
        [1] 상속(Inheritance)
         : Java에서 상속은 부모클래스의 필드, 메소드, 생성자를
           자식클래스가 물려 받아 사용가능하게 해주는 것.
         : 부모가 자식에게 물려주는 것이 상속의 기본 개념
         : Java에서 상속은 자식이 부모의 것을 물려 받는다.

        [2] extends
         : class가 class를 상속받을 때 사용
         : interface가 interface를 상속받을 때 사용
         : 부모에서 선언/ 정의를 모두 하고, 자식은 필드나 메소드를 그대로 사용할 수 있다.
         : 다중 상속이 불가능! 1개의 클래스만 상속 받을 수 있다.

        [3] implements(interface 구현)
         : 부모는 선언만 한다. (필드에 값을 부여하지 않고, 메소드에 내용을 작성하지 않는다.)
         : 자식은 오버라이딩(재정의)을 통해 사용해야 한다.

         ※ 오버로딩 vs 오버라이딩 차이점!
          - 오버로딩(overlooding) : 같은 이름의 메소드를 여러개 가지면서,
                                   매개변수 유형과 갯수를 다르게 하는 기술
                    ex) void power(String TV),  void power(int rul) >> 매개변수완 관련되어 있다  != 상속이란 전혀 상관없다!!

          - 오버라이딩(overriding) : 부모클래스가 가지고 있는 필드,
                                   메소드를 자식클래스가 재정의해서 사용하는 기술
     */

}

 

다중 상속은 불가능 하나의 상속만 사용가능!

[1] 기본적인 상속방법

// 먼저 Parent라는 class 생성

public class Parent {

    // 필드
    int parentVar = 10;

    // 메소드
    void parentMethod(int a, int b){
        System.out.println("부모클래스의 메소드! ");
    }
    // 생성자 : 기본생성자(생략)
}

// 그다음 상속받을 대상 Child을 지정해서 Parent를 불어온다

public class Child extends Parent{ // 현재 상속을 받았는지 불가능!!

    // 필드
    // int parenVar =10; (상속받은 내용 생략된 상태)
    int childVar = 20;

    // 메소드
    void  childMethod(){
        System.out.println("자식 메소드! ");
    }

    // 오버라이딩
    @Override
    void parentMethod(int a, int b) {
        // 부모 클래스의 메소드 내용을 실행!!
//        super.parentMethod(a, b);

        // 부모클래스의 메소드 내용을 실행하지 않고 재정의
        System.out.println("부모클래스 메소드 내용 재정의");
    }


    // 오버로딩
    void abc(){
        System.out.println("오버로딩1");
    }

    void abc(int a){
        System.out.println("오버로딩2");
    }

    void abc(String b){
        System.out.println("오버로딩3");
    }
    // 생성자 : 기본생성자(생략)
}

 

extends의 상속 받았는지는 눈으로 알수 가 없다

 

오버라이딩의 개념!!

 

오버로딩의 개념!! 매개변수안에 다른 변수 선언시 사용!!

// 둘다 상속을 이용한걸 P_C_Main라는 class를 새로 만들어 각각에 부모, 자식 객체 생성해주고 

// 생성한 객체에 필드값과 메소드로 확인하는 작업을 가진다.

public class P_C_Main {
    public static void main(String[] args) {

        // 부모클래스 객체 생성
        Parent parent = new Parent();

        // 자식클래스 객체 생성
        Child child = new Child();

        // 부모클래스의 필드값, 메소드 확인
        System.out.println("parentVar : " + parent.parentVar);
        parent.parentMethod(1, 2);

        System.out.println();
        // 자식클래스의 필드값, 메소드 확인
        System.out.println("childVar : " + child.childVar);
        child.childMethod();
        System.out.println();

        // 상속한 필드값, 메소드 확인
        System.out.println("상속받은Var : " + child.parentVar); // 오버라이딩을 통해서 값이 변함!
        child.parentMethod(1,2);
        System.out.println();

        // 오버로딩 확인  >> 실행하는 내용이 가각 다르다!
        child.abc();
        child.abc(0);
        child.abc("id");
    }
}

 

부모를 자식으로 부터 불러와서 그대루 쓰고 > 데이터 타입별로 오버로딩한다.


[2] 기본적인 상속방법2

// class 상속 3개 만들어서 mainclass 결과 확인하기!!

// sup클래스

// 할아버지 클래스
public class Sup {

    // 필드
    int x = 90;

    // 메소드
    void supMethod(){
        System.out.println("할아버지 클래스 메소드!");
    }
}

// sub클래스

// 부모클래스(할아버지 클래스를 상속)
public class Sub extends Sup{

    // 필드
    int y =20;

    // 메소드
    void subMethod(){
        System.out.println("부모클래스 메소드");
    }
}

// subsub클래스

// 자식클래스(부모클래스 상속)
public class SubSub extends  Sub{

    // 필드
    int z = 30;

    // 메소드
    void  subSubMethod(){
        System.out.println("자식클래스 메소드");
    }
}

// sub_sub_Main클래스 결과값 호출

public class Sup_Sub_Main {
    public static void main(String[] args) {
        // 자식객체 생성
        SubSub subi = new SubSub();

        // 자식클래스 필드, 메소드
        System.out.println("subi.z : " + subi.z);
        subi.subSubMethod();

        // 부모클래스 필드, 메소드
        System.out.println("subi.y : " + subi.y);
        subi.subMethod();

        // 할아버지클래스 필드, 메소드
        System.out.println("subi.x : " + subi.x);
        subi.subMethod();
        }
       }

// 결과

 

extens랄는걸루 상속을 받아 사용할수 있다!!


[3] 기본적인 상속방법3

// 각 class 생성 후 상속받을 대상 지정후 Mainclass에서 출력값확인

// Employee1 클래스 생성 (필드, 메소드)!!!

public class Employee1 {

    // 필드
    String name;  // 이름
    String dept;   // 부서
    int salary;     // 급여

    // 메소드 : 직원정보
    String getEmployeeInfo(){
        return "이름 : " + name + ", 부서 : " + dept + ", 급여 : "+ salary;
    }
}

// Employee1 클래스에서 상속받을 Salesman1(필드랑 메소드 생성)

// Employee1 클래스 상속
public class Salesman1 extends  Employee1{

    // 새로운 필드값
    int commission;     // 수당

    // 상속받는 salary를 재정의
    int salary = 100;

    // 직원정보 메소드 재정의
    String getEmployeeInfo(){
        return  super.getEmployeeInfo() + ", 수당 : " + commission;
    }

    String getEmployeeInfo1() {
        return "이름 : " + name + ", 부서 : " + dept + ", 급여 : "+ salary+ ", 수당 : "+ commission;
    }
}

// SalesMain에서 상속 받은 값 출력

public class SalesMain {
    public static void main(String[] args) {

        // 매개변수 생성자로 객체 생성
        Salesman2 salesman2 = new Salesman2("김정태", "영업팀", 200, 100);

        System.out.println(salesman2.getEmployeeInfo());
        System.out.println(salesman2.getEmployeeInfo1());
    }
}

// 출력값


[3] 기본적인 상속방법3-1

//  각 class 생성 후 상속받을 대상 지정후 Mainclass에서 출력값확인

// Employee2 클래스 생성 (필드, 메소드)!!!

public class Employee2 {
    String name;  // 이름
    String dept;   // 부서
    int salary;     // 급여

    // 기본생성자
    public Employee2() {

    }
    // 매개변수 생성자
    public Employee2(String name, String dept, int salary) {
        this.name = name;
        this.dept = dept;
        this.salary = salary;
    }
    // 메소드 : 직원정보
    String getEmployeeInfo(){
        return "이름 : " + name + ", 부서 : " + dept + ", 급여 : "+ salary;
    }
}

// Employee2 클래스에서 상속받을 Salesman2(필드랑 메소드 생성)

public class Salesman2  extends  Employee2{

    // 새로운 필드값
    int commission;     // 수당

    // 상속받는 salary를 재정의
    int salary = 300;

    // 직원정보 메소드 재정의
    String getEmployeeInfo(){
        return  super.getEmployeeInfo() + ", 수당 : " + commission;
    }


    String getEmployeeInfo1() {
        return "이름 : " + name + ", 부서 : " + dept + ", 급여 : "+ salary+ ", 수당 : "+ commission;
    }

    // 기본생성자

    public Salesman2() {
        super();
    }

    // 매개변수생성자  >> commission만 추가!!
    public Salesman2(String name, String dept, int salary, int commission) {
        super(name, dept, salary);     // 상속받은거 변경
        this.commission = commission;  // 상속받을거 그대로 사용
    }
}

// SalesMain1에서 상속 받은 값 출력

public class SalesMain1 {
    public static void main(String[] args) {

        // Salesman 객체 생성
        Salesman1 salesman1 = new Salesman1();

        salesman1.name = "김정태";
        salesman1.dept = "영업팀";

        salesman1.commission = 100;

        System.out.println("getEmployeeInfo() 메소드 : 상속받음");
        System.out.println(salesman1.getEmployeeInfo());
        System.out.println();

        System.out.println("getEmployeeInfo() 메소드 : 상속받지 않음");
        System.out.println(salesman1.getEmployeeInfo1());
    }
}

// 출력

 

 

 

 

상속 받은건 == 0;
상속 받지 않은건 그대루 넘어간다!!


[4] 기본적인 상속방법

//  각 class 생성 후 상속받을 대상 지정후 Mainclass에서 출력값확인

// person 클래스 생성 (필드, 메소드)!!!

public class person {

    // 사람
    // 교육생, 선생님, 직원

    // 필드
    String name;
    int age;
    String phone;
    
    // 메소드
    void  finish(){
        System.out.println("인천일보 아카데미는 9시에 문을 닫는다.");
    }

}

 

// Student 클래스 생성 (필드, 메소드, 오버라이드)!!! 재정의 작업!!!

public class Student extends  person{

    // String name;
    // int age;
    // String phone;

    String classroom;
    int grade;

    // 재정의 작업
    @Override
    void finish(){
        System.out.println("교육생은 4시 50분에 퇴실한다.");
    }
    /*
    void finish(){
        System.out.println("인천일보 9시에 끝남");
    }
     */

}

// teacher 클래스 생성 (필드, 메소드, 오버라이드)!!! 재정의 작업!!!

public class teacher extends person{

//    String name;
//    int age;
//    String phone;

    // 다시 고유값 지정!!(새로운값)
    int salary;
    String subject;

    // 메소드 (공통되는 값)
    @Override
    void  finish(){
        System.out.println("선생님은 5시에 퇴근~~");
    }
}

// Worker 클래스 생성 (필드, 메소드, 오버라이드)!!! 재정의 작업!!!

public class Worker extends person{

    // 필드
    String department;

    // 메소드
    @Override
    public  void finish(){
        System.out.println("직원들은 6시에 퇴근!!");
    }
}

상속되었다!!(눈에는 보이지 않지만)ㅎㅎ

// Info클래스 생성(메소드 정의)

public class Info {

    void finishType(person type){
        type.finish();
    }
}

// ICIAMain을 출력!!

// 다형성 기억하기!

// 다형성 : 하나의 객체(info)에서
// 여러타입(person, student, teacher, worker)
// 참조할 수 있는 방식을 제공해준다.
public class ICIAMain {
    public static void main(String[] args) {
        // Info 객체
        Info info = new Info();

        // Person, Student, Teacher, Worker 객체
        person person = new person();
        Student student = new Student();
        teacher teacher  = new teacher();
        Worker worker = new Worker();

        // 다형성 : 하나의 객체(info)에서
        // 여러타입(person, student, teacher, worker)을
        // 참조할 수 있는 방식을 제공해준다.

        info.finishType(person);
        info.finishType(student);
        info.finishType(teacher);
        info.finishType(worker);
    }
}

class에 따라 자식이 부모에게 가면 추상적이고 부모가 자식에게 가면 구체화라고 한다.

// 출력

public class ICIAMain {
    public static void main(String[] args) {
        // Info 객체
        Info info = new Info();

        // Person, Student, Teacher, Worker 객체
        person person = new person();
        Student student = new Student();
        teacher teacher  = new teacher();
        Worker worker = new Worker();

        // 다형성 : 하나의 객체(info)에서
        // 여러타입(person, student, teacher, worker)을
        // 참조할 수 있는 방식을 제공해준다.

        info.finishType(person);
        info.finishType(student);
        info.finishType(teacher);
        info.finishType(worker);
    }
}

[5] 추상클래스의 상속방법

// pulic과 class사이에 abstract를 적어줬다!!!
// 추상 클래스 만드는법!!
public abstract class Abstract {

    /*
        (1)pulic과 class사이에 abstract를 적어줬다!!!
        (2)추상 클래스
            - 구체적이지 않은 클래스
            - 추상메소드를 꼭 포함!
            - 추상메소드는 반드시 자식클래스에서 재정의!!
     */


    // 일반메소드
    public void move(){

    }

    // 추상메소드
    public abstract void sound();
    // 중괄호{}가 없다 + 세미클론(;) 추가
    // public(접근제한자)과 void(데이터타입) 사이에 abstract 추가

    // { 구현부 } 없이 이름만 선언하는 메소드
    // 추상메소드를 만들면 반드시 class에도 abstract를 추가
}

// 무조건 구현부에 abstract!!! 로 바꿔줘야 추상클래스로 사용할 수 있다.


[6] 추상클래스의 상속방법 (예제)

// Animal이라는 클래스 생성

public abstract class Animal {

    // 일반메소드
    public void breathe(){
        System.out.println("숨을 쉬다. ");
    }

    //  추상메소드
    public abstract void move();
    public abstract void sound();
}

// Animal에 상속받는 Dog와 Cat클래스 생성

public class Cat extends Animal{

    @Override
    public void move() {

    }

    @Override
    public void sound() {
        System.out.println("야옹!");
    }
}
public class Dog extends Animal{
    @Override
    public void move() {

    }

    @Override
    public void sound() {
        System.out.println("멍멍! ");
    }
}

// 유틸클래스 받을수 있도록 클래스 생성

// 아무것도 상속 xxxx
public class AnimalUtil {

    public void  animalSound(Animal animal){
        animal.sound();
    }

    public void animalMove(Animal animal){
        animal.move();
    }
}

// 출력 받을수 있게 Main에 지정해줘서 결과값 확인!

// main은 아무것도 상속 받지 않고 실행만!!
public class AnimalMain {
    public static void main(String[] args) {
        // 강아지, 고양이 객체 생성

        Dog dog = new Dog();
        Cat cat = new Cat();

        System.out.println("====== [1] 객체생성 ======");
//        dog.breathe();
        dog.sound();

//        cat.breathe();
        cat.sound();

        System.out.println();
        System.out.println("====== [2] 자동 타입 변환 ======");
        Animal animal = null;

        // 업캐스팅(Upcasting)
        // : 하위클래스가 상위클래스 타입으로 자동 타입 변환하는 것
        animal = new Dog();
        animal.sound();


        animal = new Cat();
        animal.sound();

        System.out.println();
        System.out.println("====== [3] 유틸클래스 활용 ======");
        // 유틸객체
        AnimalUtil util = new AnimalUtil();
        util.animalSound(dog);
        util.animalSound(cat);

        System.out.println();
        System.out.println("====== [4] 추상클래스 객체 ======");
        Animal ani = null;
//      Animal ani1 = new Animal();  >> 안됨(공간을 만들어둠)
       // Animal (추상클래스)는 객체를 만들수 없다!
    }
}

추상메소드 사용법
(업캐스팅)다형성!! 다른 출력 결과


[6] 추상클래스의 상속방법 (예제2)

// Computer라는 객체 추상클래스 생성

public abstract class Computer {
    // 일반메소드
    public  void  turnOn(){
        System.out.println("전원을 켭니다.");
    }

    public  void  turnOff(){
        System.out.println("전원을 끕니다.");
    }

    // 추상메소드
    public abstract  void  display();
    public abstract  void  typing();

}

추상메소드를 사용하기 위한 지정!!

// Desktop과 Notebook클래스 생성

public class Desktop extends Computer{
    @Override
    public void display() {
        System.out.println("데스크탑 모니터를 활성화 합니다.");

    }

    @Override
    public void typing() {
        System.out.println("데스크탑 키보드로 타이핑 합니다.");
    }
}

 

public class Notebook extends Computer{

    // Desktip과 Notebook 클래스에서 Computer클래스를 상속
    // 추상메소드를 재정의 (내용 작성x)

    @Override
    public void display() {
        System.out.println("노트북 모니터를 활성화 합니다.");
    }

    @Override
    public void typing() {
        System.out.println("노트북 키보드로 타이핑 합니다.");
    }
}

// ComputerUtil클래스 생성

//- ComputerUtil 클래스 생성
// 아무것도 상속XXX
public class CompuerUtil {

    // Computer타입의 객체
    // computer은 추상클래스의 객체를 만들지 못하므로 탈락
    // Computer클래스를 상속받은 Desktop의 객체나 Notebook의 객체는 사용가능

//    public void Computerdisplay(Computer computer){
//        computer.display();
//    }
//    public void Computertyping(Computer computer){
//        computer.typing();
//    }

    public void ComputerMothod(Computer computer){
        computer.display();
        computer.typing();
    }
}

// 출력 받을수 있게 Main에 지정해줘서 결과값 확인!

public class CompuerMain {
    public static void main(String[] args) {

        // 모니터 출력, 타자 입력
        // (1)객체생성 방법
        // (2)자동타입변환 방법
        // (3)유틸클래스 사용방법
        // - ComputerUtil 클래스 생성
        // - ComputerMethod() 생성

        Desktop desktop = new Desktop();
        Notebook notebook = new Notebook();

        System.out.println("(1)객체생성 방법");
        desktop.display();
        notebook.display();
        desktop.typing();
        notebook.typing();


        System.out.println();
        System.out.println("(2)자동타입변환 방법");
        // Computer는 추상클래스이기 때문에 객체를 생성할 수 없다
        Computer computer = null;

        computer = new Desktop();
        computer.display();
        computer.typing();
        computer = new Notebook();
        computer.display();
        computer.typing();

        //- ComputerUtil 클래스 생성
        System.out.println();
        System.out.println("(3)유틸클래스 사용방법");
        Desktop desktop1 = new Desktop();
        Notebook notebook1 = new Notebook();

        // - ComputerMethod() 생성
        CompuerUtil compuerUtil = new CompuerUtil();
        compuerUtil.ComputerMothod(desktop1);
        compuerUtil.ComputerMothod(notebook1);
    }
}

// 출력