본문 바로가기

Server Programming/BackEnd Project

28일차- 자바. 인터페이스와 내부클래스

반응형

인터페이스 - 외부에 공개를 위한 스펙 명세

  1. 공통된 메서드를 가지는 클래스를 추상 메서드로 묶거나 관련없는 클래스들을 인터페이스 타입으로 묶기위해 사용한다.
  2. 표준화 가능 - 스펙을 정의하고 제시하므로 일관성있는 코드 가능
  3. 다중 상속 가능
  4. 협업이 쉬워지므로, 개발 시간 단축
  5. 느스한 결합이 가능 - 변경에 유연하다. (DIP : 의존성 역전 원칙)
  6. 서로 관계 없는 클래스 간의 관계를 맺을 수 있다.
  7. 다중의 인터페이스를 구현하게 되면 구현한 클래스는 참조변수를 인터페이스 타입으로 선언해 사용 가능

인터페이스의 작성 규칙

  1. 정적 상수와 추상 메서드만을 선언 가능하므로, 추성클래스와 같이 인스턴스 생성 불가 (예외 존재)
  2. Java 8 : default method, static method 선언 가능
  3. Java 9 : private mehtod 선언 가능
  4. 인터페이스는 최상위 인터페이스가 존재하지 않는다.
  5. 인터페이스 상속시 사용하는 extends 키워드는 클래스에서 인터페이스 구현을 위해 사용하는 implements 키워드 보다 먼저 선언해야 한다.
  6. implements 선언한 클래스는 인터페이스에 정의된 추상메서드를 구현해야 한다.
  7. 모든 메서드는 public abstract이며 작성하지 않으면 컴파일러가 추가한다.
  8. 모든 멤버변수는 public static final이며 작성하지 않으면 컴파일러가 추가한다.

 

인터페이스 다형성

  1. 인터페이스 타입을 참조 변수로 선언할 수 있다.
  2. 인터페이스 메서드 선언시 Argument 타입이나 return type으로 지정 가능

-> 인터페이스 타입을 참조변수로 선언한다면, 인터페이스를 구현한 클래스의 객체를 인터페이스 타입의 참조변수로 다룰 수 있다.

-> 인터페이스 타입을 매개변수로 지정한다면, 인터페이스를 구현한 클래스만 매개변수로 올 수 있다.

-> 인터페이스 타입을 메서드의 리턴타입으로 지정한다면, 인터페이스를 구현한 클래스의 객체만 반환한다.

 

 

인터페이스 UML

  1. 스테레오 타입으로 선언
  2. 추상메서드는 이태릭체로 표현

 

마커 인터페이스

  • 멤버를 정의하지 않고 클래스의 용도를 선언하는 빈 인터페이스
  • 컴파일러나 JVM에게 이러한 기능 할 수 있다고 정보를 제공하기 위한 인터페이스

 

#직렬화 Serialiazable

  • 일반적으로 만드는 객체는 
  • 직렬화하면 객체의 멤버 변수들을 비트로 변환해 흘러보내 복원해서 사용하기 위한 곳으로 보낸다.
  • 받은 곳에서는 역직렬화를 수행해 복원해서 사용한다.
    • objectinputstream, objectoutputstream
    • 사용하는 이유
      • 직렬화를 통해 무수히 많은 관계의 객체를 원격지에서 사용할 수 있다.

 

#복제화 Clonable

  • 복제 가능한 클래스

 

상속과 구현을 복합적으로 사용한다면

-> 반드시 UML을 작성해 구성한 후에 기능을 구현하도록 한다.

 

인터페이스에 의한 다중 상속

  • 여러 인터페이스에서 필요한 메서드만 조합해서 구현 가능
  • 여러 인터페이스를 구현한 경우에 선언한 타입의 인터페이스 메서드만 호출 가능
    • 타입 다형성

디폴트 / 정적 / private 메서드

  • 디폴트 메서드나 정적 메서드 추가되어도 클래스의 소스 변경 없이 동작해 호환성을 유지할 수 있다.
  • 인터페이스에 디폴트 메서드, static 메서드 추가 (JDK 1.8)
  • 디폴트 메서드의 경우 default 선언을 한 메서드로, 구현한 모든 클래스에서 사용 가능하고, 오버라이딩 역시 가능하다.
  • 정적 메서드의 경우 인터페이스명을 통해 객체 생성없이 호출 가능하다.
  • private 메서드의 경우 인터페이스 내에서만 사용 가능한 메서드로, 디폴트 메서드나 정적 메서드에서 사용하기 위해 구현한 메서드다.
    • default method의 동일 코드를 private method로 추출해 재사용할 수 있도록 한다.
    • 원하지 않게 상속 받은 메서드를 오버라이드 하는 오류를 제거할 수 있다.

 

package ch11.defaultmethod;

interface Drawable{

    //추상메서드 -> 클래스에서 구현 필요
    void draw();

    //디폴트 메서드
    //디폴트 메서드에서 필요한 메서드를 private으로 선언해 사용한다.
    default void msg(){
        System.out.println("interface default method");
        privateMsg();
    }
    //정적 메서드
    //정적 메서드에서 필요한 메서드를 
    static void staticMsg() {
        System.out.println("interface static method");
        privateStaticMsg();
    }
    //인터페이스의 디폴트 메서드와 정적 메서드에서만 사용하고,구현한 클래스에서는 재사용 불가능하도록 private 선언한 메서드
    private void privateMsg(){
        System.out.println("\t-> interface private method");
    }
    private static void privateStaticMsg(){
       System.out.println("\t-> interface private static method");
    }
}
class Rectangle implements Drawable{
    @Override
    public void draw(){
        System.out.println("Rectangle class draw method");
    }
}
public class TestInfDefaulMethod {
    public static void main(String args[]){
        Drawable d=new Rectangle();
        d.draw();
        d.msg();
        Drawable.staticMsg();
    }
}

 

중첩 인터페이스

  • 클래스에 인터페이스 선언
  • 인터페이스에 인터페이스 선언 -> 그룹화해서 사용하기 위해 선언한다. 안에서만 그룹화하므로 관리가 용이
  • 외부에서는 참조해서 사용해야하고 직접 액세스 불가
  • 중첩 인터페이스의 경우 인터페이스내에서 선언하면 Public이어야 하며, 클래스 내에서 선언된 경우 모든 접근제어자 사용가능
  • 중첩 인터페이스는 static으로 선언
  • 클래스내에 중첩 인터페이스를 선언하는 이유는 해당 클래스와 긴밀한 관계를 맺는 구현 클래스를 만들기 위함
  • 중첩인터페이스 구현과 객체 생성시에는 외부인터페이스.내부인터페이스명으로 선언한다.
package ch11.nestedinf;

interface printable{
    void print();
    interface MessagePrintable{
        void msg();
    }
}

 

package ch11.nestedinf;

interface Showable{
    void show();
    // 중첩 인터페이스 Message
    interface Message{
        void msg();
    }
}
class TestNestedInterface implements Showable.Message{
    @Override
    public void msg() {
        System.out.println("안녕! nested interface");
    }

    public static void main(String args[]){
        Showable.Message message = new TestNestedInterface();
        message.msg();
    }
}

 

내부클래스

  • 내부클래스도 외부클래스의 멤버로 볼 수 있다. (변수 / 메서드/ 생성자/ 내부클래스)
  • Inner class내에 메소드를 구현하게 되면 아래와 같이 접근하여 실행
  • Top-Level의 인스턴스를 생성 > Inner 클래스 생성>Inner인스턴스명.메소드명()으로 접근
  • Outer outer = new Outer();
    Outer.Inner inner = outer.new Inner();
    inner.innerMethod();

내부클래스의 장점

  • Outer 클래스의 private을 포함한 모든 멤버에 접근 가능
  • 클래스와 인터페이스를 한 곳에서 그룹화해 가독성이 좋고 유지 관리가 쉬운 코드 개발 가능
  • 더 적은 코드로 기능 구현 가능
  • 내부에서만 사용하기 때문에 독자적인 클래스으로는 만들기에는 아까운 경우 사용 가능
  • 외부클래스의 private 멤버를 사용하기 위해 만든 클래스

내부클래스의 유형

  • 멤버 내부 클래스 : 클래스 내부와 메서드 외부에서 생성된 클래스
  • 익명 내부 클래스 : 인터페이스를 구현하거나 클래스 확장을 위한 클래스
  • 로컬 내부 클래스 : 메서드 내에서 클래스 생성
  • 정적 중첩 클래스 : 클래스 내에 정적 클래스
  • 중첩 인터페이스 : 클래스 또는 인터페이스 내에 생성된 인터페이스

 

멤버 접근 방식 

: 외부 클래스의 인스턴스 변수 사용시에는 Outer.this.value를 이용해 접근

 

내부 클래스 변수 사용시 주의사항

  • final 변수는 contant pool에 별도로 저장하므로 사용가능
  • 로컬 내부클래스에 선언한 변수 중 final로 선언하지 않으면 메소드 종료시 메모리에 제거되므로 사용 불가 (Java 1.7 이후 제거)

 

 

 

익명 내부클래스

  • 이름이 없는 일회용 클래스로 단 하나의 객체만을 생성
  • 함수형 인터페이스에서 자주 사용하며 재사용 필요 없고, 단발성으로 사용할 경우 이용
  • 클래스 정의와 객체 생성을 동시에 한다.

로컬 내부클래스

  • 메서드 내에서 생성되는 클래스로, 메서드 블록내에 정의되고, 클래스의 멤버는 아닌 클래스
  • 클래스 멤버 변수에 접근이 가능하다.
  • 로컬 내부클래스의 메서드 호출 하기 위해서는 내부 클래스를 인스턴스를 생성해야한다.

 

정적 중첩클래스

  • 인스턴스 멤버 및 인스턴스 메서드에 접근 불가능한 클래스
  • Outer 클래스 이름으로 접근 가능
  • 외부클래스의 static 변수에 접근하기 위한 클래스

 

즉, 변수의 스코프와 똑같이 정적 중첩클래스의 경우엔 외부 클래스 객체 생성없이 생성가능하고,
인스턴스 내부 클래스의 경우 외부 클래스 인스턴스 생성후, 외부 클래스명을 통해 내부클래스 객체 생성

(static 변수 사용하는 것과 같이 사용)

 

 

 

package ch11.memberinner;

/**
 * 멤버 내부클래스
 */
public class TestMemberOuter1 {
    private int data=30;
    class Inner{
        void msg(){System.out.println("data is "+data);}
    }
    public static void main(String args[]){
        TestMemberOuter1 obj=new TestMemberOuter1();
        TestMemberOuter1.Inner in=obj.new Inner();
        in.msg();
    }
}

 

 

 

 

MSA

  • 중앙 캐시서버를 서비스들이 바라보고 있다.
  • MSA를 이용해 로딩의 시간을 최소화
  • Redis를 이용해 Elastic cache를 사용 임계치 메모리 설정하는데, 요청은 들어오지만 병목현상 발생

 

 

토이 프로젝트

  • 도서관리시스템 -> 만화책 대여 관리 시스템 개발
  • 만화책 등록 대여/반납 기능 개발
  • 클래스 다이어그램 -> 시퀀스 다이어그램 -> UML
  • 데이터 집합 관리
  • 데이터 구조 설계, 패키지 구조 설계, 빌드 및 의존성 관리

 

나중에 스프링으로 전환할 수 있도록

반응형

'Server Programming > BackEnd Project' 카테고리의 다른 글

30일차 - 자바. 예외처리  (0) 2023.01.11
29일차 - TIL  (0) 2023.01.10
28일차 -TIL  (0) 2023.01.09
27일차 -TIL  (0) 2023.01.09
26일차 -TIL  (0) 2023.01.09