⭐JAVA 클래스⭐

p_chan.log·2022년 8월 12일
0

JAVA

목록 보기
11/17

🔴객체지향 프로그래밍과 객체

💠1.객체(Object)

  • 프로그램에서 표현하고자 하는 기능을 묶기 위한 단위

1-1. 객체지향 프로그래밍

  • 객체가 중심이 되는 프로그래밍 기법

💠2.클래스

클래스와 객체의 관계

  • 객체를 생성하기 위해서는 객체의 설계도가 필요하다.

2-1. 클래스(=class)

  • 객체의 설계도 역할을 하는 프로그램 소스
  • 공장에서 하나의 설계도를 사용하여 여러 개의 제품을 생산할 수 있는 것처럼
    하나의 클래스를 통해 동일한 구조를 갖는 객체를 여러 개 생성할 수 있다.

2-2. 객체를 구성하는 단위

  • 객체를 이루는 것은 데이터와 기능이다.
  • 데이터는 변수로 표현된다.
    -> 객체 안에 포함된 변수를 '멤버변수' 또는 '프로퍼티'라 한다.
  • 기능은 메서드(=함수)로 표현된다.

2-3. 클래스의 기본 작성 방법

  • 'class'라는 예약어와 클래스의 이름을 명시하고 {..}블록을 구성한다.
  • 멤버변수는 여러개 존재할 수 있다. 이때, 값을 선언과 동시에 할당할 수도 있고,
    객체를 통해 간접적으로 할당할 수도 있다.
  • 메서드는 여러 개 존재할 수 있다.
  • 클래스안에 포함된 멤버변수와 메서드를 특성에 따라 그룹화 하기 위한 기법이 클래스를
    작성하는 것이라고 이해할 수 있다.

2-4. 객체의 생성 방법

  • 객체의 선언
    클래스이름 객체이름;
  • 객체의 할당
    객체이름 = new 클래스이름();
  • 선언과 할당의 통합
    클래스이름 객체이름 = new 클래스이름();

2-5. 객체의 사용

  • 객체 안에 포함된 변수나 메서드는 점(.)으로 연결하여 접근한다.
  • 객체안에 포함된 변수의 값을 다른 변수에 복사하는 경우
    • 변수 = 객체이름.멤버변수;
  • 객체안에 포함된 변수의 값에 다른 값을 대입하는 경우
    • 객체이름.멤버변수 = 값;
  • 객체 안에 포함된 메서드를 호출하는 경우
    • 객체이름.메서드이름();
  • 객체 안에 포함된 메서드에 파라미터를 전달하는 경우
    • 객체이름.메서드이름(값1, 값2, ...);
  • 같은 클래스를 통하여 생성된 객체라 할지라도 서로 다른 값을 대입하면 서로 독립적인
    형태로 존재하게 된다.
  • 값이 대입되지 않은 멤버변수를 갖는 클래스
    -> 클래스란 객체를 위한 틀을 제공하는 것이기 때문에, 클래스 작성과정에서
    멤버변수에 대입된 값은, 객체를 통하여 멤버변수의 값을 지정하기 전까지
    사용될 "기본값"으로서의 의미이다.
    -> 객체를 통하여 새로운 값이 대입되면 클래스 작성시에 멤버변수에 대입한 값은
    의미를 잃어버리게 된다
    -> 때문에 일반적으로 클래스 작성시에는 멤버변수에 값을 지정하지 않는다.

2-6. 메서드를 포함하는 클래스

  • 메서드란 프로그램에서 하나의 동작 단위를 의미한다.
  • 두 개 이상의 메서드가 서로 동일한 대상을 위해서 존재할 경우,
    이 메서드들을 클래스에 포함시켜 그룹화 할 수 있다.
  • 클래스에 멤버변수와 메서드가 공존할 경우, 멤버변수는 모든 메서드가 공유하는 전역변수로
    존재하게 된다.

변수의 종류 -> 멤버변수(=전역변수)
: 클래스 안에서 선언된 변수로서, 클래스 블록범위 안에서 유효하다.
-> 지역변수
: 메서드 안에서 선언된 변수로서, 메서드의 블록을 빠져나가지 못한다.
그러므로 다른 메서드는 해당 변수를 인식하지 못한다. 이 규칙은
조건, 반복문과 같은 블록{}을 형성하는 모든 경우에 해당한다.

2-7. 메서드만을 포함하는 클래스

  • 객체안에 멤버변수(=데이터)가 포함되지 않는다.
  • 객체안에 포함된 메서드를 호출하여 결과를 만들기 위한 목적이므로, 굳이 여러 개의
    객체를 생성할 필요가 없다.

💠3. this

3-1. 자기 자신을 의미하는 키워드

  • 클래스 안에서 this를 사용하여 "자기자신"을 표현한다.

3-2. this를 사용해서 지역변수와 멤버변수 구분하기

class User{
	String name;		// 전역변수
	public void setName(){
		String name;	// 지역변수
		name = "사용자";
		this.name = "자바학생";
	}
}
-> 멤버변수(전역변수)와 지역변수가 동일한 이름으로 공존할 경우,
유효성의 범위가 작은 변수가 우선적으로 인식된다.
-------------------------------------------------------------------------
  class Student{
	String name;	   // 전역변수
	public void setName( String name ){
		this.name = name;
    }
 }	
  • -> 파라미터도 해당 메서드 안에서만 유효한 지역변수의 일종이다.
  • -> 파라미터를 사용하여 멤버변수의 값을 간접적으로 설정하고자 할 경우,
    변수의 이름을 서로 다르게 사용하는 것보다는 이름은 동일하게 지정하고
    this 키워드를 사용하여 멤버변수와 파라미터를 구별하는 것이 java언어의 일반적인
    처리 방식이다.
  • -> 모든 멤버변수 앞에는 this 키워드를 사용하여 멤버변수임을 직관적으로 표시하는
    것이 소스코드의 가독성을 위해서 바람직하다.

3-3. 현재 클래스의 메서드를 의미하는 용도로서의 this

class User{
	public String getName(){
		String name = "자바학생";
		return name;
	}		
	public void sayName(){
		String myname = this.getName();
		System.out.println(myname);
	}
}
  • -> getName()을 호출하는 메서드는 this키워드를 사용하여 현재 클래스 안에
    포함된 다른 메서드임을 명시하고있다.
  • -> 하지만 메서드의 경우 다른 클래스의 메서드를 이름만으로 호출할 수 있는 방법이
    없기때문에, this.getName() 가 아닌, getName()만 사용하더라고 코드 가독성의
    문제는 없기때문에 잘 사용하지 않는다.

💠4. 생성자

Member m1 = new Member();

4-1. 생성자란

  • new 키워드를 사용하여 객체가 생성될 때 자동으로 실행되는 특수한 형태의 메서드
  • 리턴형을 명시하지 않으며, 메서드의 이름은 클래스와 동일하다.
User user = new `User()`;
class User{
	User(){
		// 이 안은 객체가 생성될 때 자동으로 호출된다.
	}
}
  • 자동으로 실행된다는 특성 때문에, 객체가 생성되면서 해당 객체의 특성을 초기화
    하기 위하여 사용된다.(ex:멤버변수의 초기값을 할당하는 용도)

4-2. 기본 생성자

  • 파라미터가 없는 생성자
  • 클래스에 특별히 생성자가 정의되지 않은 경우, Java컴파일러가
    기본생성자가 존재한다고 인식한다.
User u = new User();
class User{
	User(){
		// 생성자는 있지만, 내용은 비어있다.
	}
}

4-3. 파라미터를 갖는 생성자

  • 생성자도 메서드의 한 종류이므로 파라미터를 함께 정의하는 것이 가능하다.
  • 생성자의 파라미터를 멤버변수에 복사하는 것으로 객체의 초기화를 외부적인 요인에
    의해 처리할 수 있다.

💠5. 은닉성

5-1. 은닉성 이란?

  • 멤버변수나 메서드가 객체에 노출되지 않도록 설정하는 기법
  • 객체를 사용하는 측의 실수로 인한 기능의 오작동을 방지하기 위해, 클래스의 일부를
    숨기는 처리를 말한다.

5-2. 적용하는 방법

  • 변수의 이름이나 메서드 이름 앞에 "접근 한정자"를 지정한다.

public
- 모든 곳에서 접근 가능하다.
- 일반적으로 모든 메서드 앞에 명시한다.

private
- 클래스 안에서 사용가능하고, 객체를 통해 접근할 수 없다.
- 일반적으로 모든 멤버변수 앞에 명시한다.

protected
- 현재 클래스 내의 다른 자원이나, 같은 패키지 안에 존재하는 클래스와
하위 클래스에서 접근 가능하다. 잘 사용하지 않는다.

default
- 접근 한정자를 명시하지 않은 경우. 현재 클래스 내의 다른 자원이나
동일 패키지 내의 다른 클래스에서 접근 가능하다. 잘 사용하지 않는다.

5-3. getter, setter

  • 멤버변수가 은닉된 형태로 선언된 경우 프로그램의 가장 근본적인 목적인 데이터에
    접근하는 방법이 사라지므로, 메서드를 통하여 간접적으로 접근하는 방법이 마련되어야 한다.
  • getter, setter는 은닉된 멤버변수에 간접적으로 접근하기 위하여 정의된 메서드들을
    의미하는 용어이다.

getter -> 은닉된 멤버 변수의 값을 리턴하기 위한 메서드
setter -> 파라미터로 전달된 값을 멤버변수에 복사하기 위한 메서드

5-4. 클래스의 접근 한정자

public
-> 객체 생성 가능하다.
-> 서로 다른 소스코드에 정의된 클래스끼리도 객체 생성이 가능하다.

private
-> 클래스에 적용할 수 없다.

protected
-> 클래스에 적용할 수 없다.

default
-> 동일할 소스코드에 정의된 클래스끼리만 객체로 생성 가능하다.
(지금까지 예제 형태)

5-5. 클래스의 분리

  • 하나의 소스코드에서 프로그램의 모든 기능을 구현하게 되면 유지보수에 비효율적 이므로,
    기능단위로 소스코드를 분리해야 한다.
  • 소스코드가 분리된 클래스끼리는 public이 명시되어야만 서로 객체 생성이 가능하다.
  • 일반적으로 클래스 정의에는 public 접근 한정자만 사용한다.
  • 하나의 소스코드에는 하나의 public 클래스만 존재할 수 있다.

5-6. 자바빈즈(Java Beans)

  • 자바 언어에서 사용하는 복합적 데이터 표현의 최소 단위로서,
    재사용 가능한 컴포넌트(구성요소)를 생성할 수 있다.
  • 자바 빈즈 클래스로서 작동하기 위해서, 객체 클래스는 명명법, 생성법 그리고 행동에
    관련된 일련의 관례를 따라야만 한다. 이러한 관례는 개발도구에서 자바 빈즈와의
    연결을 통해 클래스의 사용과 재사용 그래고 클래스의 재배치를 가능하게 한다.
  • 지켜야할 관례
    -> 클래스는 생성자를 가지고 있어야한다.
    -> 클래스의 속성들은 get, set 메서드를 통해 접근할 수 있어야 한다.

💠6. 상속성

6-1. 클래스 간의 상속이란?

  • 클래스간에는 부모-자식의 상속 관계를 설정할 수 있다.
  • 부모클래스 A를 자식클래스 B가 상속받을 때, B는 A의 모든 멤버변수와 메서드를
    자신의 것으로 상속받게 된다.
    (단, private으로 설정된 기능은 상속되지 않는다)

6-2. 상속 정의 방법

  • extends 키워드를 사용하여 부모 클래스의 이름을 명시한다.

public class 자식클래스 extends 부모클래스{.....}

6-3. 클래스 다이어그램을 통한 상속의 표현

  • 클래스의 구조를 표현하는 클래스 다이어그램에서, 상속은 자식 클래스가 부모클래스를
    가리키는 화살표로 표현한다.
  • 상속관계가 이루어 질 때 부모 클래스를 super 클래스 라고 한다.

6-4. 상속을 활용

  • 기존에 존재하는 클래스의 소스 수정 없이 기능을 확장하고자 하는 경우
  • CalcChild 클래스는 CalcParent클래스를 상속받기 때문에, 별도의 소스코딩 없이도
    plus(), minus() 메서드를 포함하게 된다.
  • CalcChild 클래스에 times(), divide() 메서드를 추가하면, 상속받은 메서드에 새로운 기능을
    추가하는 효과를 얻을수 있다.

  • 여러 개의 클래스에서 공통되는 기능을 추출하여 공유하기
  • 질문/답변 게시물의 한 단위를 표현하기 위한 QNAArticle 클래스와 자료실의 게시물을
    표현하기 위한 FileArticle은 글 번호와 제목이라는 공통된 특성을 갖는다.
  • Article 클래스는 QNAArticle 클래스와 FileArticle 클래스가 공통적으로 포함하고 있는
    멤버변수인 "글번호(num)", "제목(title)"과 이 변수들에 대한 getter, setter를 추출한 것이다.
  • 이와 같이 공통 기능을 별도의 클래스로 추출해 내면, 코드의 재사용 및 수정이 용이하다.

💠7. 오버라이드(override)

7-1. 다형성을 구현하기 위한 Override

  • 육군(Army), 해군(Navy), 공군(AirForce) 은 Unit이라는 클래스를 통하여 공통 속성을
    정의하고 있다.
  • 공통속성은 : 이름(멤버변수 및 getter, setter), 공격(attack() 메서드)
  • 같은 이름이지만 다른 동작을 수행해야 하는 필요성
    -> 모든 군대는 '공격'이라는 공통된 특성을 갖지만 공격하는 방법은 육/해/공군이
    서로 다르게 처리되어야 한다.

7-2. 부모클래스가 갖고 있는 기능을 자식 클래스가 재정의

  • 부모 클래스에 정의된 것과 동일한 이름을 갖는 메서드를 자식 클래스가 정의한 경우,
    부모 클래스의 기능은 자식에게 가려진다.
  • 이렇게 부모의 기능을 재정의 하는 것을 메서드 Override라 한다.
  • 하나의 이름으로 다양한 효과 얻기
    -> 모든 자식클래스가 동일한 이름의 메서드를 갖게 되므로 각 객체에 대하여
    attack()이라는 이름을 사용하여 서로 다른 형태를 구현할 수 있게 된다.

7-3. Override / super

1. super

1-1. super 키워드

  • 클래스의 상속관계에서 자식 클래스가 부모 클래스를 가리키는 예약어

1-2. 사용방법

  • 멤버변수 이름 앞에 명시
    -> 부모 클래스의 멤버변수를 의미한다. 하지만 부모클래스의 멤버변수는
    이미 모두 상속되어 있기 때문에 이 경우에는 this 키워드를 사용하는
    것과 동일한 결과이기에 잘 사용하지 않는다.
  • 메서드 이름 앞에 명시
    -> 부모 클래스의 메서드를 의미한다.
    -> 재정의 되지 않은 메서드 : 이미 상속되어 있기 때문에 this 키워드를
    사용하는 것과 동일한 결과를 갖는다.
    -> 재정의된 메서드 : Override 된 메서드 이름 앞에 사용하게 되면
    재정의 되기 이전의 원본 메서드를 의미한다.
  • 키워드 자체를 메서드처럼 사용
    -> 부모 클래스의 생성자를 의미한다.

1-3 그림 설명

  • super(2/4) 설명
    -> Hello 클래스가 Korean에 상속되고, Korean클래스가 say() 메서드를
    Override 처리하게 되면 Korean 클래스의 객체는 더 이상 부모의
    say() 메서드에 접근할 수 없게 된다.

  • super(3/4) 설명
    -> 만약 부모 클래스가 가지고 있는 say()메서드에 추가적인 기능을
    구현하고자 한다면 부모의 코드를 그대로 복사해서 사용해야 할 것이다
    원본 기능에 대한 수정이 발생할 경우 부모 클래스와 자식 클래스를
    모두 수정해야 하기 때문에 소스코드의 유지보수 효율성이
    떨어지게 된다.

  • super(4/4) 설명
    -> super 키워드는 부모 클래스의 메서드를 호출하는 기능을 가지고
    있기 때문에, Override된 자식 클래스의 메서드에서 super 키워드를
    사용하면, 재정의 되기 이전의 부모 클래스에 대한 메서드를
    호출할 수 있다.

1-5. 상속관계에서의 생성자 처리

  • 생성자는 상속되지 않는다.
  • 하지만 생성자가 정의된 클래스는 객체 생성을 위해 생성자 파라미터를
    반드시 전달 받아야 하기 때문에, 파라미터를 갖는 생성자가 정의된
    클래스를 상속받게 되면 에러가 발생한다.

1-6. 부모 생성자의 강제 호출

  • 생성자가 정의된 클래스를 상속받은 경우에는 자식 클래스의 생성자를
    통해서 부모 생성자를 강제로 호출해야 한다.
  • 부모의 생성자를 호출하는 방법은 super키워드를 메서드 이름으로
    사용하는 것이다.

1-7. 메서드 재정의 과정에서 오타가 발생한 경우

  • 부모 클래스의 'say()'메서드를 재정의 하는 과정에서 개발자의 실수로
    'sai()' 라고 메서드가 추가되었다면, Java는 새로운 메서드가 추가한
    것으로 인식하고 특별한 에러를 표시하지 않는다.

1-8. 메서드 재정의 과정에서의 오타 방지 옵션

  • "@Override"는 이 키워드가 명시된 위치 아래에 정의되는 메서드가
    부모 클래스에 존재하지 않을 경우 구문 에러로 처리한다.
  • 부모 클래스의 메서드를 재정의 하고자 할 경우, 의도치 않은 실수를
    예방하기 위한 '오타 방지용 옵션' 이다.
  • 여러 개의 메서드를 재정의 한다면 재정의 되는 모든 메서드들 위에 각기
    명시해 한다.

💠8. 오버로드(overload)

8-1. 메서드 오버로드(Overload)

  • 원칙적으로 하나의 클래스 안에는 동일한 이름의 메서드가 두개 이상
    존재할 수 없지만, 이를 가능하게 하는 예외적인 처리 기법

8-2. 이름이 동일한 메서드를 정의하기 위한 조건

  • 메서드간의 파라미터가 서로 달라야한다.
    -> 파라미터의 데이터 타입이 다르다.
    ( 데이터 형이 동일하고 변수의 이름이 다른경우는 동일한 파라미터로
    인식된다)
    -> 파라미터의 개수가 다르다.
    -> 서로 다른 데이터형을 갖는 파라미터들의 전달 순서가 다르다.
  • 리턴형이 다른 경우는 오버로드의 성립에 아무런 영향을 주지 않는다.

8-3. 오버로드 예시

  • 파라미터의 데이터형이 서로 다르기 때문에 오버로드 성립

    public void user(int a){ .. }
    public void user(long a){ .. }

  • 파라미터의 개수가 서로 다르기 때문에 오버로드 성립

    public void user( int a ){..}
    public void user( int a, int b ){..}

  • 데이터 형의 전달 순서가 서로 다르기 때문에 오버로드 성립

    public void user(int a, String b){..}
    public void user(String b, int a ){..}

  • 오버로드 성립 불가

    public void user(int a, String b){...}
    public void user(int b, String a){...}

8-4. 생성자의 Overload

  • 객체 생성 방법의 다양화
  • 생성자 역시 메서드의 한 종류이므로 Overload가 가능하다
  • 생성자를 Overload 할 경우, 해당 클래스에 대해 '객체를 생성하는 방법'을
    다양하게 준비할 수 있게 된다.

8-5. this 키워드를 사용한 생성자 Overload

  • this 키워드의 용법
    -> 메서드처럼 사용할 경우, 현재 클래스의 다른 생성자를 의미한다.
  • this 키워드를 사용하여 생성자 Overload를 간결하게 처리하기
    -> 파라미터가 서로 다른 생성자들이 하나의 완전한 생성자를 호출하도록 하여,
    데이터의 초기화를 한 곳에서 일괄적으로 처리하도록 구현할 수 있다.

💠9. 객체 형변환

9-1. 객체 형변환

  • java 기본 유형의 데이터들처럼 객체 참조변수의 경우에도 형변환(casting)이
    이루어 진다.
  • 서로 다른 클래스 유형으로부터 나온 객체 참조변수들 간의 대입에는
    일정한 규칙이 있다.
Parent parent = new Child();
  • 왼쪽 항(부모 클래스)과 오른쪽 항(자식 클래스)의 객체 유형이 서로 다른 경우,
    두 유형이 서로 상속 관계에 있고 왼쪽 객체(부모 클래스)가 오른쪽 객체(자식클래스)
    의 상위 클래스인 경우에만 암묵적 형변환이 일어난다.
  • 하위 클래스에서 상위클래스 유형으로 할당하는 것은 가능하나 그 반대의 경우에는
    명시적 형변환을 해야한다.
    -> 그러나 상위 클래스 유형을 하위 클래스 유형으로 강제 형 변환하는
    경우에는 할당되는 객체의 유형에 따라서 실행 오류가 발생할 수 있다.

9-2. 객체간의 암묵적 형변환

A a1 = new B();
A a2 = new X();
------------------
A a3 = new C();
A a4 = new Y();
------------------
B b1 = new C();
X x1 = new Y();
------------------
C c = new C();
B b2 = c;
------------------
Y y = new Y();
X x2 = y;

9-3. 암묵적 형변환과 메서드 오버라이드

  • 암묵적 형변환은 부모를 상속받는 자식객체의 기능을 부모에게
    물려받은기능만 사용하도록 제한한다.
  • 그러므로 암묵적 형변환이 발생하게 되면 오버라이드된 기능만 사용가능
    하고, 추가적으로 구현한 기능은 사용할 수 없다.
  • 주의할 점은 기능의 제한이지 기능의 변경은 아니다.
Unit u1 = new Army();
Unit u2 = new Navy();
Unit u3 = new AirForce();	
u1.attack();
u2.attack();
u3.attack();
  • 상속관계의 객체를 부모형태로 변환하면 클래스의 종류를 구분하지 않고
    일관된 기능을 호출할 수 있다.
  • 객체가 상위클래스형태로 형변환 되더라도 Override된 자신의 기능은
    잃지 않는다.
  • 하지만, 추가적으로 구현했던 기능은 사용할 수 없게 되므로
    원래의 기능을 다시 사용할 수 있는 방법이 필요해졌다.

9-4. 명시적 형변환

  • 부모 클래스의 객체를 자식 클래스 형태로 변환하는 것
  • 형변환을 위해서는 변환할 클래스 이름을 명시적으로 지정해 주어야 한다.
ChildClass child = (ChildClass)parent;

9-5. 명시적 형변환의 조건

  • 객체가 최초 생성될 때 자식 클래스 형태로 생성되고,
    부모 형태로 암묵적 형변환이 된 상태를 다시 원래 자식 클래스 형태로
    되돌릴 경우에만 가능하다.
ChildClass child1 = new ChildClass();
ParentClass parent = child1;		// 암묵적 형변환
ChildClass child2 = (ChildClass)parent;

9-6. 명시적 형변환이 가능한 경우

Army army1 = new Army();
Unit u = army1;
Army army2 = (Army)u;
----------------------
Unit u = new Navy();
Navy navy = (Navy)u;

9-7. 불가능한 경우

-> 최초 객체 생성이 부모 형태로 만들어진 경우 불가능하다.
Unit u = new Unit();
Army army = (Army)u;
-------------------------------
-> 최초 생성된 것과 다른 형식으로 변환하는 것은 불가능 하다.
Army army = new Army();
Unit u = army;
Navy navy = (Navy)u;

=> 위의 두 경우 모두 문법적인 오류는 없기 때문에,
이클립스에서는 에러를 검출하지 못한다. 하지만 프로그램을 실행
시켰을 경우에는 에러가 발생한다.

💠10. 객체배열

10-1. 객체배열

  • 일반 데이터 타입의 배열과 동일한 개념으로, 같은 클래스의 객체 여러
    개를 그룹화 할 수 있다.
  • 일반 데이터형의 배열 생성과 객체 배열 생성 비교
일반 데이터 형 배열의 경우
int[] data = new int[3];
객체 배열의 경우
Army[] data = new Army[3];	

10-2. 각 경우에 대한 배열의 요소 할당 처리

  • 일반 데이터형은 단순히 값을 대입하지만, 객체 배열은 'new'를
    사용해서 객체를 할당해야 한다.
일반 데이터 형 배열의 경우
data[0] = 1;
data[2] = 2;
data[3] = 3;
객체 배열의 경우
data[0] = new Army();
data[1] = new Army();
data[2] = new Army();

10-3. 부모 클래스의 배열에 자식 클래스의 객체를 넣기

  • 배열의 생성이 부모 클래스로 지정되었을 경우, 모든 자식 클래스의
    객체들은 그 배열에 포함될 수 있다.
Unit[] unit = new Unit[3];
// 배열의 요소 할당 과정에서 암묵적 형변환이 이루어 진다.
unit[0] = new Army();
unit[1] = new Navy();
unit[2] = new AirForce();

10-4. 객체 배열의 활용

  • 일괄처리가 가능
    -> 서로 다른 객체를 부모 형태의 배열에 담게 되면, 반복문으로
    일괄처리가 가능하다.
    -> 이 때 배열의 각 요소를 통해 사용하는 메서드가 Override되어
    있을 경우, 부모의 메서드가 아니라 자신이 재정의한 기능을 뜻한다.
for( int i = 0; i<unit.length; i++ ){
	unit[i].attack();
}

  • 원래의 기능으로 복귀하기
    -> 배열의 각 요소가 확장한 기능을 사용하기 위해서는
    원래의 클래스 형태로 명시적 형변환이 이루어 져야 한다.
    -> 하지만 반복적으로 처리되는 과정에서 몇 번째 요소가 어떤 클래스에서
    최초 생성 되었는지를 판단하기란 쉽지 않다.
  • instanceof 연산자
    -> instanceof 연산자는 어떤 객체에 대한 출처를 판단하여
    boolean 형으로 결과를 반환한다
if( unit[0] instanceof Army ){
	Army temp = (Army)unit[0];
}

💠11. 추상화

11-1. 상속성과 다형성의 필요성

  • 상속성은 객체간의 공통적인 기능을 관리하기 위한 기법으로,
    코드의 재사용을 통하여 프로그램의 유지보수를 편리하게 한다.
  • 다형성(Override, Overload)은 서로 다른 기능이지만 메서드의 이름을
    공통되게 처리함으로서 전체 프로그램의 일관성을 유지하게 한다.

11-2. Override 처리의 문제 발생 가능성

  • '@Override' 키워드를 사용하지 않고 메서드를 재정의 하는 과정에서
    메서드 이름에 실수가 발생하더라도 에러가 아닌 새로운 메서드의
    정의로 인식되므로 의도하지 않은 실행결과를 가져올 수 있다.
  • '@Override' 키워드를 사용하더라도 자식 클래스를 구현하는 개발자의 실수로
    부모의 기능을 재정의 하지 않았다면, 다형성의 구현은 이루어지지 않게된다.

11-3. 상속 처리시, Override를 강제하기

  • 추상화 기법은 특정 클래스를 상속받은 경우, 부모의 특정 메서드들을
    무조건 재정의하도록 강제하는 기법이다.
  • 특정 메서드를 재정의하도록 강제함으로써, 자식 클래스들을 작성하기 위한
    가이드의 역할을 할 수 있다.
  • 즉, 추상화 기법은 java 클래스를 작성하기 위한 설계도를 소스코드
    형태로 제시하는 역할을 한다.

11-4. 추상 메서드 만들기

  • 추상 메서드를 정의하기 위해서는 'abstract' 키워드를 사용하여 메서드를
    정의한다.
  • 추상 메서드는 자식 클래스가 구현해야 하는 메서드의 가이드라인만 제시하기
    위한 목적으로 사용되기 때문에, 선언만 가능하고 구현부가 없다.
// 선언만 가능하고, 구현부를 위한 블록이 존재하지 않는다.
public abstract void move();

11-5. 추상 메서드를 포함한 클래스

  • 추상 메서드를 하나 이상 포함하고 있는 클래스는 반드시 '추상 클래스'로
    정의되어야 한다.
  • 추상 클래스는 'abstract' 키워드를 사용하여 정의할 수 있다.
// 추상 클래스의 정의
public abstract class Hello{
	public abstract void move();
}

  • 추상 클래스는 객체를 생성할 수 없고, 반드시 상속을 통해서만 사용될 수
    있다. 즉 추상 클래스는 다른 자식 클래스를 위한 '가이드라인'의 역할을 한다.

11-6. 공통 기능과 설계 제시를 모두 처리

  • 추상 클래스는 생성자, 멤버변수, 일반 메서드등을 포함할 수 있다.
  • 즉 공통 기능과 가이드라인을 모두 정하여 다른 클래스에게 상속된다.
public abstract class Hello{
	// 멤버변수
	private String msg;
	// 생성자
	public Hello( String msg ){ this.msg = msg; }
	// 일반 메서드
	public String getMsg(){ return this.msg; }
	// 선언만 되고, 구현부를 위한 블록이 존재하지 않는다.
	public abstract void sayHello();
}

💠12. 인터페이스

12-1.추상 클래스의 한계

  • 자바 클래스 간의 상속에는 하나의 부모만 존재할 수 있기 때문에,
    앞의 상황에서 요구하는 다중 상속의 구현은 불가능하다.

12-2. Interface란?

  • 완벽한 추상화를 구현하기위한 java Class의 한 종류이다.
  • 다중 상속이 가능하기 때문에 용도별로 세분화 하여 필요한 요소만 상속할
    수 있다.

12-3. 비교

  • 추상클래스
    -> 멤버변수, 생성자, 메서드, 추상메서드를 포함할 수 있다.
    -> 이 클래스를 상속받는 자식 클래스는 다른 클래스를 상속받을 수
    없다.
    -> 객체의 생성이 불가능하다
  • 인터페이스
    -> 추상메서드만 포함할 수 있다.
    -> 인터페이스는 다중 상속이 가능하다.
    -> 객체의 생성이 불가능하다.

12-4. 인터페이스 상속을 위한 implements 키워드

  • 인터페이스의 상속은 implements 키워드를 사용한다.
  • 인터페이스도 추상화를 구현하고 있기 때문에, 인터페이스를 상속받는
    클래스는 인터페이스 내의 모든 메서드들을 반드시 재정의 해야 한다.

12-5. 인터페이스의 다중 상속

  • 인터페이스는 콤마(,)로 연결하여 여러 개를 동시에 상속 받을 수 있다.
    public class Monster implements Fight, Move{	
              ........................
     }
  • 필요한 경우 다른 클래스와 동시에 상속받을 수 있다.
    public class Monster extends User implements Fight,Move{      
                ..........................
     }

💠13. Static

public class Article{
	private static int count;		// 전체 글 수
	private static String category;	// 카테고리

	private int num;		// 글 번호
	private String title;		// 글 제목
	private String regDate;		// 날짜
}
  • 멤버변수는 모든 객체가 독립적으로 갖는 고유 데이터이기 때문에
    게시물의 수라는 공유 데이터를 모든 게시물이 갖게 된다.
  • 즉, 각각의 객체가 중복된 데이터를 갖게 된다.
  • 클래스를 설계할 때, 멤버변수 중 모든 객체에서 공통적으로 사용해야
    하는 값에 static 을 붙인다.
  • static이 붙은 멤버변수는 객체의 개수에 상관 없이 단 하나만 생성되며,
    이를 모든 객체가 공유하기 때문에 메모리를 효율적으로 사용할 수 있다.

13-1. 컴퓨터의 메모리 구조

  • 코드영역(고정영역)
    -> 프로그램의 코드가 저장되는 영역
    이 영역에서 저장된 명령어들을 CPU가 하나씩 가져가 실행한다.
  • 데이터영역(고정영역)
    -> 전역변수와 static으로 선언된 변수가 할당된다.
    이 영역에 할당되는 변수들은 프로그램 시작과 동시에 메모리 공간이
    할당되어 종료될 때까지 남아있게 된다.
  • 힙영역(동적 영역)
    -> 프로그래머가 원하는 시점에 변수를 할당하고 소멸 시키는 영역
    메모리 동적 할당시 사용된다.객체가 생성되는 영역이다.
  • 스택 영역(동적 영역)
    -> 함수가 실행될 때 사용되는 파라미터와 지역변수에 대한 메모리 공간.
    함수의 종료와 함께 소멸된다.

13-2. 하나의 프로그램이 사용하는 메모리영역

  • 고정영역
    -> 프로그램이 실행되면 실행파일이 메모리에 로드 된다.
    실행파일의 용량만큼 메모리를 사용한다.
    -> 실행파일의 크기는 변할 수 없으므로 이 영역의 크기는 고정 크기를
    갖는다.
  • 동적영역
    -> 프로그래머가 new 키워드를 사용해서 객체나 배열을 생성하면
    사용된다. (힙영역)
    -> 메서드가 호출되는 동안 사용될 파라미터와 지역변수가 생성된다.
    (스택영역)
    -> 메서드가 종료되나 객체가 더이상 사용되지 않으면 생성된 변수나
    객체는 메모리에서 사라지므로, 이 영역은 유동적인 크기를 갖게 된다.

13-3. static 데이터의 생성 위치

  • static 데이터는 메모리의 고정영역 중 데이터영역에 생성되고,
    일반 멤버변수나 객체는 동적영역중 Heap 메모리 영역에 생성된다.

13-4. 프로그램이 메모리를 사용하는 순서

  • 최초 실행시 고정 영역에 실행파일만큼의 메모리를 점유한다.
  • 프로그램이 각종 동작을 수행하는 동안 동적 영역을 사용한다.

13-5. 멤버변수와 static 멤버변수의 차이

  • static 변수는 프로그램의 실행과 동시에 객체의 생성 여부와 상관 없이
    이미 존재하기 때문에 소스 코드에는 특정 클래스 안에 명시하지만,
    그 클래스를 통해서 생성되는 객체나 그 안에 포함되는 멤버변수와는
    다른 존재이다.
  • 객체가 생성되지 않더라도 이미 존재하고 있기 때문에 static 변수는
    객체의 이름을 통해 접근하는 것이 아니라, 클래스의 이름을 통해서
    접근해야 한다.
  • 단, static 변수가 선언된 클래스 안에서는 변수 이름으로 직접 접근
    허용된다.
- Article 클래스 및 다른 클래스에서 접근하는 경우
	Article.coutn = 5;
	Article.category = "공지사항";
-----------------------------------------
- Article 클래스 내부에서 접근하는 경우
	count = 6;
	category = "공지사항";

13-6. static 데이터에 접근하기 위한 메서드

  • 클래스에서 정의하는 일반 메서드들은 객체의 생성과 동시에 동적 메모리
    영역에서 활성화 된다.
    -> 동적 메모리 영역의 입장에서는 고정 메모리 영역의 자원들은
    항상 존재한다.
    -> 고정 메모리 영역의 자원들은 동적 메모리의 자원들이 항상 존재하는
    것이라는 보장을 받지 못한다.
  • 그러므로 객체의 생성과 상관 없이 static 변수에 접근하기 위한 메서드를
    만들 필요 있을때, 메서드의 정의 과정에서 static키워드를 사용하면
    static 자원에 접근하기 위한 메서드를 만들 수 있다.
public staic void setCount(int count){
	Article.count = count;
}
  • 메모리 영역의 차이 때문에 static 메서드는 동적 메모리 영역의 멤버변수를
    사용하거나, static이 아닌 일반 함수를 호출할 수 없다.

💠14. Package

  • 패키지 -> 클래스에 대한 묶음 단위
  • 클래스를 용도별이나, 기능별로 그룹화 한 것을 말한다. 소스코드는 폴더로
    분류된 형태로 존재하게 된다.
  • 서로 다른 패키지에 속해 있다면 다른 클래스와 이름이 동일하더라도
    충돌이 발생하지 않는다.
  • 패키지 이름은 회사 + 프로젝트의 아이덴티티를 넣는다.
  • com.koreait.shop.article

14-1. 복사된 소스파일

  • 패키지에 소속된 클래스 파일은 첫 번째 라인에서 자신이 소속된 클래스 패키지
    이름을 선언해야 한다.

💠15. ClassPath란?

  • 컴파일이 완료된 *.class 파일들이 위치하는 경로
  • 즉 객체를 생성할때 대상 클래스의 소스 없이도 컴파일된 결과물만 참조하여
    객체 생성 및 메서드 호출 등이 가능해 진다.

💠16. 라이브러리

  • 한개 이상의 패키지들을 배포하기 용이하도록 압축한 형태
  • 다른 프로그램에서 라이브러리 안에 포함된 기능을 활용할 수 있다.

💠17. JAVA기본 API들

  • 우리가 사용하는 JDK 안에는 이미 수많은 라이브러리가 포함되어 있고,
    이 라이브러리 안에는 프로그램 개발에 필요핸 패키지들이 기본적으로 포함되어 있다.
  • 자바 프로그래밍은 이러한 라이브러리들의 기능을 활용하여 이루어진다.
  • 이렇게 프로그램 개발을 위하여 기본적으로 제공되는 기능들을 API라 한다.

💠18. Wrapper Class

18-1. Wrapper Class란

  • Java는 데이터를 관리하기 위하여 기본 데이터 타입을 지원하지만,
    클래스를 통해서 만들어진 객체를 통한 데이터 관리도 가능하다.
  • 기본 데이터 타입의 변수를 객체형태로 사용해야 하는 경우가 있는데,
    이때 기본형 타입을 객체로 포장할 필요가 있따.
  • 포장 클래스(Wrapper Class)는 특정 기본형 타입을 나타내는 용도로 사용된다.

18-2. Wrapper Class 종류


18-3. Wrapper Class 의미

  • 초창기 Java언어는 기본 자료형의 연산보다도 Wrapper 클래스를 사용한
    연산이 더 많이 이루어 졌으나, Java언어가 발전함에 따라서 기본 자료형과
    Wrapper 클래스 간에 연산에 차이가 없어졌다.
  • 최근데 Java언어는 Wrapper클래스와 기본 자료형을 구분하지 않고 사용하기
    때문에 객체로서의 특별한 의미가 없어졌따고 볼 수 있다.

18-4. Wrapper 클래스의 객체 만들기

  • 각각의 Wrapper 클래스의 객체는 자신과 대응되는 기본 자료형의 데이터를
    파라미터로 전달받는다.
int num = 1;
Integer wrapper = new Integer( num );

18-5. Wrapper 클래스 형변환

  • 기본 자료형과 Wrapper 클래스 간에는 서로 암묵적 형변환이 가능하다.
int num = 100;
Integer wrapper = num;
---------------------------------
Integer wrapper = New Integer(200);
int num = wrapper;

18-6. Wrapper 클래스의 static 데이터

  • 모든 Wrapper클래스는 static 데이터 형태로 Wrapper 클래스에 대응되는
    자료형에 대한 최소값과 최대값을 가지고 있다.
int max = Integer.MAX_VALUE;
int min = Integer.MIN_VALUE;

18-7. 문자열 데이터의 형변환(중요)

  • 1과 "1"의 차이
  • 기본 자료형과 문자열 데이터간의 연산에서는 기본 자료형 데이터가
    문자열로 변환된 후, 문자열간의 연산으로 처리된다.
int a = 1;
String b = "1";
System.out.println(a + b);	// 11
  • 사용자 입력값에 대한 연산
  • 모든 프로그램 플랫폼에서 사용자의 입력값은 String 으로 처리된다.
  • 만약, 인터넷뱅킹에서 2개의 계좌로 송금할 금액을 각각 입력하였을 때,
    총 금액을 계산한다면 다음과 같이 처리된다.
String money1 = "3000";
String money2 = "5000";
String total = moeny1 + money2;	// 30005000
  • 문자열 데이터를 기본 데이터 형으로 변환하기
    -> wrapper 클래스에는 기본 자료형의 모양을 띄고 있는 문자열 데이터를
    실제 기본 자료형으로 변환시키는 기능이 포함되어 있다.
String money1 = "3000";
String money2 = "5000";
-----------------------------------
int m1 = Integer.parseInt( money1 );
int m2 = Integer.parseInt( money2 );
----------------------------------------
System.out.println(m1 + m2);	// 8000

💠.19.Math 클래스 개요

19-1. 수학적 연산을 지원하는 클래스

  • Math 클래스는 흔히 계산을 하는데 도움이 되는 많은 수의 기본적 수학
    함수들을 제공한다.
  • Math 클래스는 Java 표준 클래스 라이브러리의 java.lang 패키지에
    정의되어있다.
  • Math 클래스의 모든 메서드들은 static 메서드로,클래스의 객체를 생성하지
    않고 그 메서드가 정의된 클래스 이름을 통해 호출될 수 있다.

💠20. String

  • 문자열에서 정보를 추출하기 위한 String
profile
개발자 박찬의 노트

0개의 댓글