java는 객체지향언어로써 코드간에 관계를 맺어 줌으로써 보다 유기적인 프로그램을 구성할 수 있음
객체의 속성을 정해놓은 것
멤버변수 : 클래스 내부의 정보
인스턴스 : 클래스로부터 만들어진 객체를 그 클래스의 인스턴스라 함
# Phone이라는 클래스에 galaxy, iPhone이라는 인스턴스
class Phone {
String model;
String color;
int price;
}
public class Main {
public static void main(String[] args) {
Phone galaxy = new Phone(); // [생성된 인스턴스].[멤버변수] 로 멤버변수에 접근
galaxy.model = "Galaxy10";
galaxy.color = "Black";
galaxy.price = 100;
Phone iphone = new Phone();
iphone.model = "iPhoneX";
iphone.color = "Black";
iphone.price = 200;
System.out.println("철수는 이번에 " + galaxy.model + galaxy.color + " + 색상을 " + galaxy.price + "만원에 샀다.");
System.out.println("영희는 이번에 " + iphone.model + iphone.color + " + 색상을 " + iphone.price + "만원에 샀다.");
}
}
어떠한 작업을 수행하는 코드를 하나로 묶어 놓은 것
int[] heights = new int[5]; // 키가 들어가 있는 배열
initHeight(heights); // 1. 키에 대한 초기화
sortHeight(heights); // 2. 키를 오름차순으로 정렬
printHeight(heights); // 3. 정렬된 키를 출력
class Calculation {
// 반환타입 메소드(타입 변수명)
int add(int x,int y) { // add 메소드, return의 반환타입 int
return x + y;
}
int subtract(int x, int y) { // subtarct 메소드
return x - y;
}
}
public class Main { // void : 반환타입 없음(메소드 내에서 출력할 때)
public static void main(String[] args) {
Calculation calculation = new Calculation();
int addResult = calculation.add(1, 2);
int substractResult = calculation.subtract(5, 3);
System.out.println(addResult);
System.out.println(substractResult);
}
}
// 3, 2
인스턴스가 생성될 때 사용되는 인스턴스 초기화 메소드
new
와 같은 키워드로 인스턴스가 새로 생성될 때, 자동으로 호출되는 메소드class Phone {
String model;
String color;
int price;
Phone() {} // 기본 생성자
Phone(String model, String color, int price) {
this.model = model; // this : 생성된 객체 자신을 가리킴
this.color = color;
this.price = price;
}
}
public class Main {
public static void main(String[] args) {
Phone galaxy = new Phone("Galaxy10", "Black", 100);
Phone iphone =new Phone("iPhoneX", "Black", 200);
System.out.println("철수는 이번에 " + galaxy.model + galaxy.color + " + 색상을 " + galaxy.price + "만원에 샀다.");
System.out.println("영희는 이번에 " + iphone.model + iphone.color + " + 색상을 " + iphone.price + "만원에 샀다.");
}
}
# extends를 이용하여 상속
claa Animal{} Animal 부모클래스
class Dog extends Animal{} ㄴ Dog 자식클래스
class Cat extends Animal{} ㄴ Cat 자식클래스
class Animal {
String name;
public void cry() {
System.out.println(name + " is crying.");
}
}
class Dog extends Animal {
Dog(String name) {
this.name = name;
}
public void swim() {
System.out.println(name + " is swimming!");
}
}
public class Main {
public static void main(String[] args) {
Dog dog = new Dog("코코"); // 자식개체에 할당
dog.cry();
dog.swim();
Animal dog2 = new Dog("미미"); // 부모개체에도 할당 가능
dog2.cry(); // 하지만 Dog로 생성한 개체
// dog2.swim(); // compile error Animal(부모)에 있는 cry만 됨
}
}
코코 is crying
코코 is swimmin
미미 is crying
# 오버로딩
public class Main {
public static void main(String[] args) {
// 변환타입은 int, long으로 다르지만 매개변수 타입과 개수는 같아서 오버로딩 아님
int add(int x, int y, int z) {
int result = x + y + z;
return result;
}
long add(int a, int b, int c) {
long result = a + b + c;
return result;
}
// 오버로딩 맞음
int add(int x, int y, int z) {
int result = x + y + z;
return result;
}
long add(int a, int b, long c) { // 매개변수 타입 다름
long result = a + b + c;
return result;
}
int add(int a, int b) { // 매개변수 개수 다름
int result = a + b;
return result;
}
}
}
# 오버라이딩
class Animal {
String name;
String color;
public void cry() {
System.out.println(name + " is crying.");
}
}
class Dog extends Animal {
Dog(String name) {
this.name = name;
}
public void cry() {
System.out.println(name + " is barking!");
}
}
public class Main {
public static void main(String[] args) {
Animal dog = new Dog("코코");
dog.cry();
}
}
외부에서의 접근을 제한하는 역할(멤버변수, 함수에 사용)
객체지향 프로그래밍이란 객체들 간읜 상호작용을 코드로 표현하는 것
접근제어자는 캡슐화가 가능할 수 있도록 돕는 도구
# pkg > ModifierTest.java
package pkg;
public class ModifierTest {
private void messageInside() {
System.out.println("This is private modifier");
}
public void messageOutside() {
System.out.println("This is public modifier");
messageInside();
}
protected void messageProtected() {
System.out.println("This is protected modifier");
}
}
# Main.java
import pkg.ModifierTest;
class Child extends ModifierTest{
void callParentProtected() {
System.out.println("call my parent's protected method");
super.messageProtected(); // super : 내가 상속받은 부모클래스를 가리키는 키워드
}
}
public class Main {
public static void main(String[] args) {
ModifierTest modifierTest = new ModifierTest();
modifierTest.messageOutside();
// modifierTest.messageInside(); private, protected 라 안됨
// modifierTest.messageProtected();
// 추가
}
}
-> This is public modifier
This is private modifier
# 추가
Child child = new Child();
child.callParentProtected();
-> call my parent's protected method
this is protected modifier
추상 메소드를 선언할 수 있는 클래스
abstract class Bird {
private int x, y, z;
void fly(int x, int y, int z) {
printLocation();
System.out.println("이동합니다.");
this.x = x;
this.y = y;
if (flyable(z)) {
this.z = z;
} else {
System.out.println("그 높이로는 날 수 없습니다");
}
printLocation();
}
abstract boolean flyable(int z);
public void printLocation() {
System.out.println("현재 위치 (" + x + ", " + y + ", " + z + ")");
}
}
class Pigeon extends Bird {
@Override
boolean flyable(int z) {
return z < 10000;
}
}
class Peacock extends Bird {
@Override
boolean flyable(int z) {
return false;
}
}
public class Main {
public static void main(String[] args) {
Bird pigeon = new Pigeon();
Bird peacock = new Peacock();
System.out.println("-- 비둘기 --");
pigeon.fly(1, 1, 3);
System.out.println("-- 공작새 --");
peacock.fly(1, 1, 3);
System.out.println("-- 비둘기 --");
pigeon.fly(3, 3, 30000);
}
}
- fly(x,y,z) 함수는 Bird를 상속받는 모든 클래스에서 동일한 동작을 하지만
그 안에서 호출된 flyable(z)의 동작만 자식 클래스에서 구현한대로 동작.
- 비둘기는 어느정도 높이까지 날 수 있고, 공작새는 전혀 날지 못하기 때문에
새의 종류마다 중복코드 없이 구현하기 위해 추상클래스, 추상메소드 사용
객체의 특정 행동의 특징을 정의하는 문법
interface 인터페이스명 {
public abstract void 추상메서드명();
}
interface Bird {
void fly(int x, int y, int z);
}
class Pigeon implements Bird{
private int x,y,z;
@Override
public void fly(int x, int y, int z) {
printLocation();
System.out.println("날아갑니다.");
this.x = x;
this.y = y;
this.z = z;
printLocation();
}
public void printLocation() {
System.out.println("현재 위치 (" + x + ", " + y + ", " + z + ")");
}
}
public class Main {
public static void main(String[] args) {
Bird bird = new Pigeon();
bird.fly(1, 2, 3);
// bird.printLocation(); // compile error
}
}
# interface인 Bird 타입으로 선언한 bird 변수는 실제로 Pigeon 객체이지만,
interface인 Bird 에 선언되지 않은 printLocation() 이라는 함수는 호출할 수 없음
# interface type으로 선언되어 있는 부분에서는 실제 객체가 무엇이든지, interface에 정의된 행동만 할 수 있습니다.
추상클래스, 인터페이스 비교
추상클래스 | 인터페이스 |
---|---|
클래스를 상속받아 이용 및 확장을 위함 | 구현하려는 객체의 동작명세 |
단일 상속 | 다중 상속 가능 |
extends 이용 | implements 이용 |
추상메소드에 대한 구현 기능 | 메소드 시그니처만 선언 가능 |
객체지향 퀴즈
1. 사람은 자식, 부모님, 조부모님이 있다.
2. 모든 사람은 이름, 나이, 현재 장소정보(x,y좌표)가 있다.
3. 모든 사람은 걸을 수 있다. 장소(x, y좌표)로 이동한다.
4. 자식과 부모님은 뛸 수 있다. 장소(x, y좌표)로 이동한다.
5. 조부모님의 기본속도는 1이다. 부모의 기본속도는 3, 자식의 기본속도는 5이다.
6. 뛸때는 속도가 기본속도대비 +2 빠르다.
7. 수영할때는 속도가 기본속도대비 +1 빠르다.
8. 자식만 수영을 할 수 있다. 장소(x, y좌표)로 이동한다.
위 요구사항을 만족하는 클래스들을 바탕으로, Main 함수를 다음 동작을 출력(`System.out.println`)하며 실행하도록 작성하시오. 이동하는 동작은 각자 순서가 맞아야 합니다.
1. 모든 종류의 사람의 인스턴스는 1개씩 생성한다.
2. 모든 사람의 처음 위치는 x,y 좌표가 (0,0)이다.
3. 모든 사람의 이름, 나이, 속도, 현재위치를 확인한다.
4. 걸을 수 있는 모든 사람이 (1, 1) 위치로 걷는다.
5. 뛸 수 있는 모든 사람은 (2,2) 위치로 뛰어간다.
6. 수영할 수 있는 모든 사람은 (3, -1)위치로 수영해서 간다.
최종정리