본문 바로가기
[언어]/JAVA

[JAVA] 자바 객체지향 문법 : 클래스와 객체, 생성자, 가비지, 접근지정자, 상속, 업/다운 캐스팅, 오버라이딩, 패키지

by seom-j 2023. 7. 7.

 

📌 클래스와 객체

클래스 : 객체 모양을 선언한 틀

    ┕  메소드(멤버 함수)와 필드(멤버 변수)는 모두 클래스 내에 구현

 

객체 : 클래스의 모양대로 생성된 실체

    ┕  객체 내 데이터에 대한 보호, 외부 접근 제한

    ┕  예를들어, 동물원 정보를 관리하기 위해 "동물"이라는 객체를 만듦

 

클래스의 상속 : 자식 클래스가 부모 클래스의 속성을 물려받고, 기능 확장

    ┕  예를들어, "동물"이라는 부모 클래스에, "기린"이라는 자식 클래스를 사용

 

객체 지향 프로그래밍

객체들간의 상호 작용으로 표현

클래스 혹은 객체들의 집합으로 프로그램 작성

 

클래스 구성

클래스 선언

    ┕  class 키워드로 선언하며, 이곳에 모든 필드와 메소드 구현

필드와 메소드

    ┕  필드 : 객체 내에 값을 저장하는 멤버 변수

    ┕  메소드 : 함수이며 객체의 행동을 구현

    ┕  예를들어, "기린"이라는 클래스에 밥을 먹었는지 여부를 확인하는 메소드 생성

필드의 접근 지정자, public

    ┕  필드나 메소드 앞에 붙어 다른 클래스의 접근 허용을 표시

    ┕  public : 다른 모든 클래스의 접근 허용

생성자

    ┕  클래스 이름과 동일한 특별 메소드

    ┕  객체가 생성될 때 자동으로 한 번 호출

    ┕  객체를 초기화하는데 필요한 코드 작성

    ┕  예를들어, "기린"이라는 클래스에 기린의 이름과 키를 초기화하는 생성자 선언

 

객체 생성 및 접근

객체 생성

    ┕  반드시 new키워드를 이용 (객체의 생성자 호출)

객체 생성 과정

    ┕  객체에 대한 레퍼런스 변수 선언 → 생성

객체의 멤버 접근

    ┕  객체 레퍼런스 멤버

 

 

📌생성자의 특징

생성자의 목적 : 객체 초기화

    ┕  예를들어, "기린"이라는 클래스에 기린의 이름과 키를 초기화하는 생성자 선언

 

생성자는 메소드임

클래스 이름과 반드시 동일

여러개 작성 가능

new를 통해 객체를 생성할 때, 객체당 한 번 호출

리턴 존재 X

객체가 생성될 때 반드시 호출됨 ➡️ 무조건 하나 이상 선언되어야 함

 

기본 생성자

매개변수 없이 단순 리턴하는 생성자

public Circle(){}

➡️ 클래스에 생성자가 하나도 선언되지 않은 경우, 컴파일러에 의해 자동 삽입

 

but, 하나라도 작성되어있을 경우 자동 삽입되지 않음.

 

 

📌 this 레퍼런스

객체 자신에 대한 레퍼런스

this.멤버 형태로 사용

클래스 내의 다른 생성자 호출

생성자 내에서만 사용 가능

반드시 생성자 코드 제일 처음에 수행

 

ex)

class Giraffa{
	String name;
	String height;
	Giraffa(String name, float height){ // 생성자
		this.name = name;
		this.height = height
	}
}

 

 

📌 객체의 치환

객체의 치환은 객체가 복사되는 것이 아니라 레퍼런스가 복사됨 (포인터 개념)

 

 

📌 객체의 배열

 

 

📌 메소드 형식

C언어의 함수와 동일

모든 메소드는 반드시 클래스 안에 있어야 함

접근지정자, 리턴타입, 메소드 이름, 인자

 

 

📌 메소드 인자 전달

기본 타입 값 전달

    ┕  값이 복사되어 전달 (리터럴)

    ┕  매개변수가 변경되어도 실인자값은 변경되지 않음

 

객체 혹은 배열 전달

    ┕  객체나 배열의 레퍼런스(포인터)만 전달

    ┕  메소드의 매개변수와 호출한 실인자 객체나 배열 공유

 

 

📌 메소드 오버로딩

이름이 같은 메소드 작성

    ┕  매개변수의 개수나 타입이 서로 다르나 이름은 동일한 메소드들

    ┕  (리턴 타입은 오버로딩과 관련 없음)

    ┕  인자에 따라 적절한 메소드 사용

 

 

📌 객체의 소멸과 가비지 커렉션

객체 소멸

    ┕  new에 의해 할당된 객체 메모리를 가상 기계의 가용 메모리로 돌려주는 행위

    ┕  자바 응용프로그램에서 임의로 객체 소멸할 수 없음

    ┕  객체 소멸은 자바 가상 기계의 고유한 역할

 

가비지

    ┕  가리키는 레퍼런스가 하나도 없는 객체 (누구도 사용할 수 없게 된 메모리)

 

가비지 컬렉션

    ┕  자바 가상 기계의 가비지 컬렉터가 자동으로 수집/반환

 

개발자에 의한 강제 가비지 컬렉션

    ┕  System or Runtime 객체의 gc() 메소드 호출

 

 

📌 자바의 접근 지정자

public : 모든 클래스에 허용

protected : 동일 패키지와 자식 클래스에 허용

디폴트(접근지정자 생략) : 동일 패키지에 허용

private : 외부로부터 완벽 차단

 

 

📌 static / non-static

non-static : 객체마다 별도로 존재

    ┕  시간적 특성 : 필드와 메소드는 객체 생성 후 비로소 사용 가능

    ┕  비공유 특성 : 멤버들은 다른 객체에 의해 공유되지 않고 배타적

 

static : 클래스 멤버

    ┕  클래스당 하나만 생성

    ┕  객체를 생성하지 않고 사용 가능

    ┕  공간적 특성 : 클래스 당 하나만 생성

    ┕  시간적 특성 : 클래스가 로딩될 때 공간 할당

    ┕  공유의 특성 : 동일한 클래스의 모든 객체에 의해 공유

 

 

📌 static의 활용

전역 변수와 전역 함수를 만들 때 활용

공유 멤버들을 작성할 때 사용 (클래스의 객체들 공유) (하나만 생성)

ex)

 

📌 static 메소드의 제약 조건

 non-static메소드 접근 불가

 this 사용 불가

 

➡️static메소드는 객체가 생성되지 않은 상황에서도 호출이 가능하기 때문

 

 

📌 final

final 클래스 - 클래스 상속 불가

final 메소드 - 오버라이딩 불가

final 필드, 상수 선언 - 선언시 초기값 지정, 실행 중 값 변경 불가

 

 

📌 상속

부모클래스(슈퍼클래스)에 만들어진 필드, 메소드를 자식클래스(서브클래스)가 물려받음

extends 키워드 사용 (슈퍼클래스를 확장한다는 개념)

상속을 통해 간결한 자식 클래스 작성

 

상속의 장점

    ┕  클래스 간결화

    ┕  관리 용이

    ┕  생산성 향상

 

 

📌 서브클래스에서의 생성자

슈퍼 클래스와 서브 클래스 각각 여러 생성자 작성 가능

 

서브 클래스 생성자 작성 원칙

    ┕  서버 클래스 생성자에서 슈퍼 클래스 생성자 하나 선택

 

서브 클래스에서 슈퍼 클래스의 생성자를 선택하지 않은 경우

    ┕  컴파일러가 자동으로 슈퍼 클래스의 기본 생성자 선택 (슈퍼클래스에 기본생성자가 없을 경우 오류 발생)

 

서브 클래스에서 슈퍼 클래스의 생성자를 선택하는 방법

    ┕  super() 이용

 

 

📌 업캐스팅

서브클래스 → 슈퍼클래스

자동 형변환

슈퍼클래스로 변경하였을 경우 슈퍼클래스의 멤버만 접근 가능

 

 

📌 다운캐스팅

슈퍼클래스 → 서브클래스

개발자의 명시적 타입 변환 필요

 

 

📌 instanceof 연산자

업캐스팅되었을 경우 객체의 타입 판단 어려움

➡️ 레퍼런스가 가리키는 객체의 타입을 불린 값으로 확인 가능

 

📌 메소드 오버라이딩

슈퍼클래스의 메소드를 서브클래스에서 재정의

    ┕  메소드 무시하기, 덮어쓰기

    ┕  서브클래스들의 자신만의 내용으로 새로 구현

    ┕  서브클래스에 오버라이딩된 메소드가 무조건 실행되는 동적 바인딩

 

 

📌 추상 메소드

선언되어 있으나 구현되어있지 않은 메소드, abstract로 선언

➡️ 서브 클래스에서 오버라이딩하여 구현해야 함

 

 

📌 추상 클래스

추상 메소드를 하나라도 가진 클래스 or 추상 메소드가 하나도 없지만 abstract로 선언된 클래스

➡️ 추상 클래스는 객체를 생성할 수 없음

 

 

📌 추상 클래스의 상속

단순 상속

    ┕  추상 클래스를 상속받아 추상 메소드를 구현하지 않으면 추상 클래스가 됨

    ┕  서브 클래스도 abstract로 선언해야 함

 

구현 상속

    ┕  서브 클래스에서 슈퍼 클래스의 추상 메소드 구현 (오버라이딩)

    ┕  서브 클래스는 추상 클래스가 아닌 것이 됨

 

 

📌 추상 클래스의 용도

슈퍼클래스에서 개념정리 후 각 서브 클래스에서 구체적 행위 구현

계층적 상속 관계를 갖는 클래스 구조를 만들 때

 

 

📌 자바의 인터페이스

클래스가 구현해야 할 메소드들이 선언되는 추상형

인터페이스 선언 - interface 키워드로 선언

➡️ 스펙을 주어 클래스들이 그 기능을 서로 다르게 구현할 수 있도록 하는 클래스의 규격 선언이며, 클래스의 다형성을 실현하는 도구임

 

 

📌 인터페이스의 구성 요소들

상수

    ┕  public 만 허용

 

추상 메소드

    ┕  public abstract 생랼 가능

 

default 메소드

    ┕  인터페이스에 코드가 작성된 메소드

    ┕  인터페이스를 구현하는 클래스에 자동 상속

    ┕  public 접근 지정만 허용 (생략 가능)

 

private 메소드

    ┕  인터페이스 내에 메소드 코드가 작서되어야 함

    ┕  인터페이스 내에 있는 다른 메소드에 의해서만 호출 가능

 

static 메소드

    ┕  public, private 모두 지정 가능 (생략할 경우 public)

 

 

📌 인터페이스의 전체적인 특징

인터페이스의 객체 생성 불가

인터페이스 타입의 레퍼런스 변수 선언 가능

인터페이스를 상속받는 클래스는 인터페이스의 모든 추상 메소드를 반드시 구현

다른 인터페이스 상속 가능

인터페이스의 다중 상속 가능

 

 

📌 인터페이스 구현

인터페이스의 추상 메소드를 모두 구현한 클래스 작성

➡️ implements 키워드 사용 (여러개의 인터페이스 동시 구현 가능)

 

 

📌추상 클래스와 인터페이스 비교

유사점

객체를 생성할 수 없고, 상속을 위한 슈퍼 클래스로만 사용

클래스의 다형성을 실현하기 위한 목적

 

차이점

 

📌 패키지 개념과 필요성

여러명이 분담하여 응용프로그램을 개발할 경우, 동일한 이름의 클래스가 존재할 가능성이 있음 ⇒ 합칠 경우 오류 발생

패키지

: 서로 관련된 클래스와 인터페이스의 컴파일 된 클래스 파일들을 하나의 디렉터리에 묶어 놓은 것

➡️ 경로명(.으로 연결)이 달라 다른 파일로 취급할 수 있도록 도와줌

 

 

📌 모듈

: 여러 패키지와 이미지 등의 자원을 모아 놓은 컨테이너

 

 

📌 패키지 사용

다른 패키지에 작성된 클래스 사용

 

import를 이용하지 않은 경우

    ┕  소스 내에서 패키지 이름과 클래스 이름의 전체 경로명을 써주어야 함

 

import를 이용하는 경우

    ┕  소스의 시작 부분에 사용하려는 패키지 명시 (소스에는 클래스만 명시하면 됨)

    ┕  특정 클래스의 경로명만 포함

    ┕  패키지 내의 모든 클래스 포함