13일차 - Java강의(예외, 제네릭)

2024. 7. 31. 20:19·Java & Spring/Java

◇ 오류와 예외

  • 오류(Error) : 일반적으로 회복이 불가능한 문제
  • 예외(Exception) : 일반적으로 회복이 가능한 문제

- 예외의 종류

  1. 코드 실행 관점에서 예외의 종류
    • 컴파일 에러 : .java파일을 .class파일로 컴파일 할 때 발생, 보통 문법오류
    • 런타임 에러 : 실행도중 맞닥뜨리는 예외
  2. 예외 처리 관점에서 예외의 종류
    • 확인된 예외(Checked Exception)
      • 컴파일 시점에서 확인
      • 반드시 예외 처리를 해줘야함
    • 미확인된 예외(UnChecked Exception)
      • 런타임 시점에서 확인
      • 예외 처리가 반드시 필요하지는 않음

◇ 예외 발생과 try-catch, finally문

  • 예외 처리 흐름
    1. 예외 정의하기
    2. 클래스, 메서드를 만들려 예외 위험 알리기(throw, throws)
    3. 위험한 메서드 사용 시 예외를 handling하기
      - try : 일단 위험이 우려되는 코드 실행을 '시도'
      - catch : 예외가 발생하면 try문 실행을 중단 시키고 catch문 진행
      - finally : 예외발생 여부와 상관없이 실행
  • 예외 처리 방법
    1. 예외 복구
      - tru-catch로 예외 처리하고 프로그램을 정상 상태로 복구
    2. 예외 처리 회피
      - 관심사를 분리해서 한 레이어에서 처리하기 위해 사용
      - throw를 이용하여 처리 회피
    3. 예외 전환
      - 예외 처리 회피와 비슷하지만, 조금 더 적적한 예외를 던져줌
  • 연결된 예외(chained exception) : 예외 안에 또 다른 예외를 포함시킴
Throwable initCause(Throwable cause) // 지정한 예외를 원인 예외로 '등록'
Throwable getCause()				 // 원인 예외를 '반환'

 

       try{
            install();
        } catch (SpaceException e){
            e.printStackTrace(0;
        } catch (MemoryException e){
            e.printStackTrace();
        } catch (Exception e) {
        	e.printStackTrace(0;
        }

위와 같은 코드에서 SpaceException과 MemoryException을 묶어 InstallException으로 예외처리를 하게되면

catch문을 줄일 수 있다(예시는 2가지 뿐이지만 여러가지라고 가정하면 효율적)

 

다음과 같이 하기 위해선 SpaceException과 MemoryException을 아래와 같이 initCause해야한다.

    public void install() throws InstallException{
        try{
            startInstall();
            copyFiles();
        } catch (SpaceException e){
            InstallException ie = new InstallEception("설치 중 예외 발생");
            ie.initCause(e);
            throw ie;
        } catch (MemoryException e){
             // 위와 동일하게 initCause 진행
        }

 

연결된 예외를 사용하면 다음과 같이 결과가 나온다.

InstallException : "설치 중 예외 발생"(대략적인 정보)

Caused by : SpaceException : "설치 할 공간이 부족합니다"(상세 정보)

 

- checked예외를 unchecked예외로 변경 할 때

throw new RuntimeException(new MemoryException("메모리가 부족합니다."));

 

→ try-catch문을 안작성해도됨


◇ 제네릭

데이터의 타입을 클래스 내부에서 지정하는 것이 아닌 외부에서 사용자에 의해 지정되는 것을 의미

 

아래 코드에서 비슷한 명령의 중복된 코드가 구현되어있다.

        class StudentPerson{
            public StudentInfo info;
            StudentPerson(StudentInfo info){ this.info = info; }
        }

        class EmployeePerson{
            public EmployeeInfo info;
            EmployeePerson(EmployeeInfo info){ this.info = info; }
        }

 

아래과 같이 제네릭화 할 수 있다.

        class EmployeeInfo{
        	public int rank;
            EmployeeInfo(int rank){ this. rank = rank;
            }
        }
            
        class Person<T, S>{
            public T info;
            public S id;
            Person(T info, S id){
            	this.info = info;
                this.id = id;
            }
        }
        
        public class Generic {
        	public static void main(String[] args) {
            	Person<EmployeeInfo, Integer> p1 
                = new Person<EmployeeInfo, Integer>(new EmployeeInfo(1), 1));
            }
        }

위 코드에서 Generic class에서 new Emolyee(1)이 Person의 T에, 1이 S에 대입되게 된다.

 

- 제네릭의 생략

        class EmployeeInfo{
        	public int rank;
            EmployeeInfo(int rank){ this. rank = rank;
            }
        }
            
        class Person<T, S>{
            public T info;
            public S id;
            Person(T info, S id){
            	this.info = info;
                this.id = id;
            }
        }
        
        public class Generic {
        	public static void main(String[] args) {
            	EmployeeInfo e = new EmployeeInfo(1);
                Integer i = new Integer(10);
            	Person<EmployeeInfo, Integer> p1 
                = new Person<EmployeeInfo, Integer>(e, i);
            }
        }

위 코드에서 아래와 같이 생략이 가능하다.

Person p1 = new Person(e, i);


- 제네릭의 제한

abstract class Info {
	public abstract int getLevel();
}

class EmployeeInfo extends Info {
	public int rank;
    EmployeeInfo(int rank) { this.rank = rank; }
    public int getLevel() {
    	return this.rank;
    }
}

class Person<T extends Info> {
	public T info;
    Person(T info){ this.info = info; }
}

public class Generic {
	public static void main(String[] args) {
    	Person p1 = new Person(new EmployeeInfo(1));
    }
}

위 코드에서

class Person<T extends Info> {}

해당 코드의 의미는 T값에 Info의 자식들만이 오도록 '강제' 하는 것이다.

class 대신 interface도 가능하다, interface를 하더라도 제네릭 상속은 implements가 아닌 extends를 사용한다.

 

'Java & Spring > Java' 카테고리의 다른 글

18일차 - Java강의(쓰레드 명령어)  (0) 2024.08.07
14일차 - Java강의(쓰레드)  (0) 2024.08.01
11일차 - Java강의(계산기 실습, 클래스화, 추상화)  (0) 2024.07.29
10일차 - Java강의(제어자, package, import, 상속, this, super)  (0) 2024.07.26
9일차 - Java강의(클래스, 필드, 생성자, 멤버, this)  (0) 2024.07.25
'Java & Spring/Java' 카테고리의 다른 글
  • 18일차 - Java강의(쓰레드 명령어)
  • 14일차 - Java강의(쓰레드)
  • 11일차 - Java강의(계산기 실습, 클래스화, 추상화)
  • 10일차 - Java강의(제어자, package, import, 상속, this, super)
DJ.Kang
DJ.Kang
백엔드 개발 기록 블로그
  • DJ.Kang
    DJ Hello World
    DJ.Kang
  • 전체
    오늘
    어제
    • 분류 전체보기
      • 이론공부
      • 시스템설계
      • Java & Spring
        • TIL
        • 트러블슈팅
        • 고도화
        • 알고리즘
        • 코딩테스트
        • Java
        • Spring
        • Thymeleaf
      • 프로젝트
        • coin-trading
        • 트러블슈팅
      • Docker
      • DB
      • AWS
      • CI-CD
      • 웹
      • git & github
      • 구인공고분석
  • 블로그 메뉴

    • 홈
  • 링크

  • 공지사항

  • 인기 글

  • 태그

    java 메서드
    데이터 타입
    java 에라토스테네스의 체
    Java 생성자
    자료구조
    java 제어자
    java
    개발로드맵
    java super
    프로그래머스 java 기초 트레이닝
    프로그래머스 java 기초트레이닝
    java 유클리드 호제법
    java기초
    Java this
    java 멤버
    java two-pointer
    java arrays.copyofrnage()
    java enhance switch
    데이터 크기
    java 세수의합
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.1
DJ.Kang
13일차 - Java강의(예외, 제네릭)
상단으로

티스토리툴바