ToBe끝판왕

[ JAVA ] 타입변환과 다형성 본문

■ 프로그래밍 SKILLS/JAVA

[ JAVA ] 타입변환과 다형성

업그레이드중 2022. 5. 23. 16:37
반응형

 


 

다형성( polymorphism )

•  같은 타입이지만, 실행 결과가 다양한 객체를 이용할 수 있는 성질

   하나의 타입에 여러 객체를 대입함으로써 다양한 기능을 이용할 수 있도록 한다.

•  부모타입에 모든 자식 객체가 대입될 수 있다.

   ( 다형성을 위해 자바는 부모 클래스로 타입 변환을 허용 )

 

 

▶ 타입변환

•  데이터 타입을 다른 데이터 타입으로 변환하는 행위

•  클래스 타입도 기본 데이터 타입변환과 마찬가지로 타입 변환이 있다.

•  클래스 타입 변환은 상속 관계에 있는 클래스 사이에서 발생

•  자식 타입은 부모 타입으로 자동 타입 변환 간으 ( 자식 < 부모 )

 

▶ 자동 타입변환( Promotion )

•  프로그램 실행 도중 자동적으로 타입변환이 일어나는 것을 뜻한다.

•  자동 타입 변환 조건

부모 클래스 변수 = 자식 클래스 타입;

•  자식은 부모의 특징과 기능을 상속받기 때문에 부모와 동일하게 취급

•  또한, 부모와 자식 사이에서 자식이 상속받는 부모가 바로 위 부모가 아니더라도 자동 타입 변환 가능

•  부모타입으로 자동타입 변환된 이후에는 부모 클래스에 선언된 필드와 메서드만이 접근 가능

   ( 예외 : 메서드가 자식 클래스에서 재정의되었다면, 자식 클래스의 메서드 대신 실행 )

 

•  예시

•  부모 클래스

public class Parent {
   // 메서드
   public void method1() {
       System.out.println( "Parent - method1()" );
   }

   public void method2() {
       System.out.println( "Parent - method2()" );
   }
}
•  자식 클래스

public class Child extends Parent {
   @Override
   public void method2() {
        System.out.println( "Child - method2()" );
   }

   public void method3() {
        System.out.println( "Child - method3()" );
   }
}
public class ChildExample {
    public static void main( String[] args ) {
       Child child = new Child();

       Parent parent = child;     // 자동 타입 변환

       parent.method1();
       parent.method2();          // 재정의된 메서드 호출( 자식 메서드 )
      // parent.method3();        // 호출 불가능
    }
}

※ 부모타입으로 자동 타입 변환된 변수는 부모클래스에 선언된 필드와 메서드만 접근이 가능하다.
※ 변수로 접근 가능한 멤버는 부모 클래스 멤버로 한정된다.

 

 

 

▶  필드의 다형성

•  다형성 : 동일한 타입을 사용하지만, 다양한 결과가 나오는 성질

•  주로 필드의 값을 다양화함으로써 실행결과가 다르게 나오도록 구현한다.

•  필드 타입은 변함이 없지만, 실행 도중에 어떤 객체를 필드로 저장하느냐에 따라 실행결과가 달라질수 있다.

   ( = 필드의 다형성 )

•  프로그래밍에서 사용되는 많은 객체들은 서로 다른 객체로 교체될 수 있어야 한다.

   이것을 프로그램으로 구현하기 위해 상속 / 오버라이딩 / 타입변환을 이용하는 것이다.

 

•  예시

•  Tire 클래스

public class Tire {
   // 필드
   public int maxRotation;             // 최대 회전수 ( 타이어 수명 )
   public int accumulatedRotation;     // 누적 회전수
   public String location;             // 타이어 위치

   // 생성자
   public Tire( String location, int maxRotation ) {    // 필드 초기화
       this.location = location;
       this.maxRotation = maxRotation;
   }

   // 메서드
   public boolean roll() {
      ++accumulatedRotation;                    // 누적 회전수 1증가
      if( accumulatedRotation < maxRotation ) { // 누적 < 최대 
          System.out.println( location + "Tire 수명 : " + 
                            ( maxRoation - accumulatedRotation ) + "회" );
          return true;
      } else {         // 누적<= 최대일 경우
          System.out.pritln( "***" + location + " Tire 펑크 *** ");
          return false;
   }
}
•  Car 클래스

public class Car {
   // 필드
   Tire frontLefttire = new Tire( "앞왼쪽", 6 );     // 위치이름, 최대 회전수
   Tire frontRightTire = new Tire( "앞오른쪽", 2 );
   Tire backLeftTire = new Tire( "뒤왼쪽", 3 );
   Tire back RightTire = new Tire( "뒤오른쪽", 4 );

   // 생성자

   // 메서드
   int run() {
       System.out.println( "[자동차가 달립니다.]" );

   // 모든 타이어 1회전, 각각 roll() 메서드 호출, 펑크시 stop() 호출, 위치 리턴
     if( frontLeftTire.roll() == false ) { 
          stop();
          return1; 
     }
     if( frontRightTire.roll() == false ) { 
          stop(); 
          return2; 
     }
     if( backLeftTire.roll() == false ) { 
          stop(); 
          return3; 
     }
     if( backRightTire.roll() == false ) { 
          stop(); 
          return4; 
     }
     return 0;
   }

   void stop() {
       System.out.println( "[자동차가 멈춥니다.]" );
   }
}
•  HankookTire 클래스

public class HankookTire extends Tire {
   // 필드

   // 생성자
   public HankookTire( String location, int maxRotation ) {
      super( location, maxRotation );
   }

   // 메서드
   @Override
   public boolean roll() {
     ++accumulatedRotation;
     if( accumulatedRotation < maxRotation ) {
        System.out.println( location + " HankookTire 수명 : " +
        (maxRotation - accumuatledRotation) + "회" );
        return true;
     } else {
         System.out.println( "***" + location + " HankookTire 펑크 *** " );
         return false;
     }
   }
}
•  KumhoTire 클래스

public class kumhoTire extends Tire {
   // 필드

   // 생성자
   public KumhoTire( String location, int maxRotation ) {
      super( location, maxRotation );
   }

   // 메서드
   @Override
   public boolean roll() {
     ++accumulatedRotation;
     if( accumulatedRotation < maxRotation ) {
        System.out.println( location + " KumhoTire 수명 : " +
        (maxRotation - accumuatledRotation) + "회" );
        return true;
     } else {
         System.out.println( "***" + location + " KumhoTire 펑크 *** " );
         return false;
     }
   }
}
•  CarExample 실행 클래스

public class CarExample {
   public static void main( String[] args ) {
      Car car = new Car();   // car 객체 생성

      for( int i=1; i<5; i++ ) {
          int problemLocation = car.run();    // car 객체의 run() 메서드 5번 반복

          switch( problemLocation ) {
            case1:
              System.out.println( "앞왼쪽 HankookTire로 교체" );
              car.frontLeftTire = new HankookTire( "앞왼쪽", 15 );
              break;
            case2:
              System.out.println( "앞오른쪽 KumhoTire로 교체" );
              car.frontRightTire = new KumhoTire( "앞으론쪽", 13 );
              break;
            case3:
              System.out.println( "뒤왼쪽 HankookTire로 교체" );
              car.backLeftTire = new HankookTire( "뒤왼쪽", 14 );
              break;
            case4:
              System.out.println( "뒤오른쪽 KumhoTire로 교체" );
              car.backRigthTire = new KumhoTire( "뒤오른쪽", 17 );
              break;
         }
      }
   }
}

※ car 객체를 만들고 car 객체의 run() 메서드를 호출, 자동차를 움직인다.
   자동차가 달리면 각 타이어의 roll(). 메서드가 실행되어 누적회전수가 증가되면서
   최대회전수가 되면, 펑크가 난다. 펑크가 나면 false값을 리턴, stop() 메서드
   실행 및 타이어의 위치값이 리턴
   리턴된 타이어의 위치값은 problemLocation변수에 저장, switch문을 통해서
   새로운 타이어로 교체

 

 

 

 

반응형
Comments