본문 바로가기
Java 공부 기록

객체지향언어와 클래스(Class)

by moonchance 2023. 6. 9.

객체지향언어의 역사

객체지향언어의 특징

 

클래스와 객체의 정의와 용도

 

객체와 인스턴스

객체의 구성요소 속성과 기능

인스턴스의 생성과 사용(1/4)

인스턴스의 생성과 사용(2/4)

인스턴스의 생성과 사용(3/4)

인스턴스의 생성과 사용(4/4)

 

[출처]자바의 정석

 

 

실습을 해보자.

public class _02_Class { // 파일명과 클래스 명이 같은 경우에만 public 사용
// 멤버변수 선언 위치
	public static void main(String[] args) {
		/* 클래스 : 설계도
		 * 객체 : 제품
		 * 메서드 : 기능
		 * 
		 * 클래스 구성
		 * - 속성(정보) : 멤버변수
		 * - 기능 : 메서드
		 * 
		 * 프린터 클래스
		 * - 속성(정보) : 크기, 색, 제조사, 제품명, 종료
		 * - 기능(메서드) : 인쇄, 복사, 스캔, 팩스
		 * 
		 * 멤버변수는 클래스 안, 메서드 밖(위) 작성
		 * 멤버변수는 클래스 안에서 사용가능(모든 메서드에서 공통적으로 사용가능)
		 * 
		 * - 객체 선언
		 * 클래스명 객체명; // 선언만 값은 null
		 * 객체명 = new 클래스명();
		 * 
		 * - 객체 선언(초기화 생성)
		 * 클래스명 객체명 = new 클래스명();
		 * 
		 * - 메서드 사용법(클래스가 다른 메서드를 호출할 경우)
		 * 객체명.메서드명();
		 * 
		 * - 같은 클래스 안에서 메서드를 호출할 경우
		 * 메서드명();
		 * - 다른 클래스 안에서 메서드를 호출할 경우
		 * 객체명.메서드명();
		 * 
		 * 
		 * 접근제한자(제어자)
		 * public : 모두 사용가능
		 * protected : 나 + 패키지 + 자식클래스
		 * (default) : 나 + 패키지
		 * private : 나
		 * public > protected > default > private
		 * 
		 * - 클래스에 public을 붙인 수 있는 경우 : 파일명 = 클래스명 같을 경우에만 가능
		 * - 멤버 변수와 멤버 메서드 public은 문제없이 사용가능
		 * - private : 멤버변수나 멤버 메서드는 다른 클래스에서 사용할 수 없다
		 * - 일반적으로 멤버변수는 private, 메서드는 public으로 선언한다
		 * - private으로 선언된 멤버 변수는 getter / setter 메서드를 만들어서 해당 변수에 접근 한다
		 * 
		 */
		point p = new point();
		p.print();
//		p.x = 1;
//		p.y = 2;
		p.save(10, 20);
		p.print();
		System.out.println(p.getX()+1);
		p.setX(30);
		p.print();
		p.setY(100);
		p.print();
		
	}

}
/* 다른 클래스 밖에서 생성
 * 접근제한자 class 클래스명{
 * }
 */
class point {
	// 멤버변수 위치
//	public int x;
//	public int y;
	private int x;
	private int y;
	
	// (x,y)
	public void print()	{
		System.out.println("(" + x + "," + y +")"); 	
	}
	// point값을 저장하는 메서드
	public void save(int x, int y) { // 매개변수로 밖에서 주는 값으로 setting
		// this : 멤버변수를 지칭하는 키워드
		this.x = x;
		this.y = y;
	}
	// getter
	public int getX() {
		return this.x;
	}
	public int getY() {
		return this.y;
	}
	// setter
	public void setX(int x) {
		this.x = x;
	}
	public void setY(int y) {
		this.y = y;
	}
	
}

getter / setter

public class _03_class2 {

	public static void main(String[] args) {
		Car c = new Car(); // 객체생성 : Car참조 인스턴스 변수c
		c.setColor("red"); // setter로 color 변경
		c.setPower(true); // setter로 전원 on
		System.out.println(c.getPower());
		c.power();
		c.power();
		c.power();
		c.power();
		System.out.println("My Car color : " + c.getColor());
		System.out.println("My Car power : " + c.getPower());
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedUp();
		System.out.println("My Car speed : " + c.getSpeed());
		c.speedDown();
		c.speedDown();
		c.speedDown();
		c.speedDown();
		c.speedDown();
		System.out.println("My Car speed : " + c.getSpeed());
	}

}
class Car { // 클래스명은 대문자로 시작
	// 멤버변수
	private String color;  // private 해당 클래스에서만 사용가능
	private boolean power;
	private int speed;


	public void power() { // 전원on, off 메서드
		power = !power; // off상태
	}
	public void speedUp() { // 속도 up 메서드
		speed++; 
	}
	public void speedDown() { // 속도 down 메서드
		speed--;
	}
	
	//getter color : private 멤버변수 color 가져다 쓰는 기능
	public String getColor() { 
		return this.color;
	}
	//setter color : private 멤버변수 color 매개변수로 초기화 하는 기능
	public void setColor(String color) {
		this.color = color;
	}
	//getter power : private 멤버변수 power 가져다 쓰는 기능
	public boolean getPower() {
		return this.power;
	}
	//setter power :private 멤버변수 power 매개변수로 초기화 하는 기능
	public void setPower(boolean power) {
		this.power = power;
	}
	//getter speed : private 멤버변수 speed 가져다 쓰는 기능
	public int getSpeed() {
		return this.speed;
	}
	//setter speed : private 멤버변수 speed 매개변수로 초기화 하는 기능
	public void setSpeed(int speed) {
		this.speed = speed;
	}
}
public class _01_Class3 {

	public static void main(String[] args) {
		Car c = new Car(); // 차의 객체가 만들어지는 상태
		// Car(); : 생성자
		
		System.out.println("메인카");
		c.setName("tiguan");
		c.setYear("2023/6");
		c.setColor("white");
		c.printCar();
		
		c.powerOn();
		c.powerOn();
		c.powerOff();
		c.powerOn();
		System.out.println(c.isPower());
		c.speedUp();
		c.speedUp();
		c.speedUp();
		c.speedDown();
		c.speedDown();
		c.speedUp();
		c.setSpeed(200);
		c.speedUp();
		c.speedDown();
		c.setSpeed(0);
		c.speedDown();
		
		System.out.println("------------------");
		System.out.println("세컨카");
		Car c2 = new Car();
		c2.setName("canival");
		c2.setYear("2020/5");
		c2.setColor("black");
		c2.printCar();
		
		Car c3 = new Car("zeta", "blue", "2021/5");
		c3.printCar();
		
		/*
		 * 객체를 생성할 때 초기값을 지정하는 것을 생성자 
		 * 생성자를 이용하면 초기화를 쉽게 할 수 있다 
		 * class를 생성하면 기본 아무것도 없는 생성자를 제공 Car() 
		 * 다른 생성자를 추가하면 기본 생성자는 사라짐 
		 * 다른 생성자를 추가 하더라도 기본 생성자를 같이 추가하여 생성자를 여러개 두는 것이 일반적
		 */
		
		/* 생성자 생성
		 * public 클래스명() {
		 *  }
		 */
	}
}
class Car { // 같은 패키지 안에서는 같은 이름의 클래스 생성 안됨
	// 멤버변수 : name, year, color, power, speed
	// final : 변수 앞에 붙이면 변경될 수 없는 값
	private String name;
	private String year;
	private String color;
	private boolean power; // boolean 초기값은 false
	private int speed;
	
	// 생성자 위치
	public Car() {
		// 기본 생성자
	}
	
	// 생성자의 매개변수 값이 다르면 가능
	/* 오버로딩(메서드 오버로딩, 생성자 오버로딩 가능)
	 * 가능조건 : 매개변수의 개수가 다름, 타입이 다름
	 */
	public Car(String name, String year, String color) {
		this.name = name;
		this.year = year;
		this.color = color;
	}
	
	// 메서드 : 내 차종의 정보를 출력하는 메서드(name, year, color)
	public void printCar() {
		System.out.printf("차종의 이름 : %s%n차종의 연식 : %s%n차종의 색깔 : %s%n", name, year, color);
		System.out.println("------------------");
	}
	// 시동켜기 : powerOn
	// power = true, 시동이 켜졌습니다.
	public void powerOn() {
		if (power) {
			System.out.println("power ON 상태 입니다.");
		}
		else {
			power = true;
		}
	}
	// 시동끄기 : powerOff
	// power= false, 시동이 꺼졌습니다.
	public void powerOff() {
		if (!power) {
			System.out.println("power OFF 상태 입니다.");
			return;
		}
		else {
			power = false;			
		}
		if (speed != 0) {
			System.out.println("시동을 끌 수 없습니다.");
		}
	}
	// 속도 올리기 : speedUp 10++
	// 최대속도 200 넘어가면 더이상 speed가 올라가지 않는다
	// power가 true인 상태에서만 동작
	public void speedUp() {
		if (power && 0 <= speed && speed < 200) {
				speed += 10;
				System.out.println("현재 속도 : " + speed);
		}
		if (speed >= 200) {
			speed = 200;
			System.out.println("최고 속도 도달");
		}
	}
	// 속도 내리기 : speedDown 10--
	// 속도가 0이되면 더이상 내려가지 않는다
	// power가 true인 상태에서만 동작
	public void speedDown() {
		if (power && 0 < speed && speed <= 200) {
				speed -= 10;
				System.out.println("현재 속도 : " + speed);
		}
		if (speed <= 0) {
			speed = 0;
			System.out.println("정지");
		}
	}
	// getter/setter
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public String getYear() {
		return year;
	}
	public void setYear(String year) {
		this.year = year;
	}
	public String getColor() {
		return color;
	}
	public void setColor(String color) {
		this.color = color;
	}
	public boolean isPower() {
		return power;
	}
	public void setPower(boolean power) {
		this.power = power;
	}
	public int getSpeed() {
		return speed;
	}
	public void setSpeed(int speed) {
		this.speed = speed;
	}
	
}
public class _02_Class4 {

	public static void main(String[] args) {
		// Card 객체를 생성하고, ♣Q 를 출력하려고 한다.
		Card c = new Card();
		c.print(); // 기본 생성자 값
		c.setShape('♣');
		c.setNum(13);
		c.print();
		c.setShape('◆');
		c.setNum(7);
		c.print();
		System.out.println(c.getNum());
		System.out.println(c.getShape());
		
		Card c1 = new Card('◆', 13); // 생성자는 인스턴스 객체를 생성할때 한번만 호출가능 ex) c1
		c1.print();
		
	}
	
}

/* Card 클래스 : 포커게임에서 사용하는 카드를 나타내는 클래스
 * 모양 : 하트(♥), 클로버(♣), 다이아(◆), 스페이드(♠)
 * 숫자 : 1 ~ 10 J Q K
 * 카드 정보를 출력
 * 
 * 클래스의 구성
 * 멤버변수 : char shape, int num
 * 생성자 : 객체 생성시 멤버변수를 초기화하는 메서드(♥1)
 * 메서드 : print, getter/setter
 */
class Card{
	private char shape;
	private int num;
	
	public Card() { // 생성자 초기 값
		this.shape = '♥';
		this.num = 1;
	}
	
	public Card(char shape, int num) {
		this.shape = shape; // 모양 ♥ ♣ ◆ ♠
		this.num = num; // 숫자
	}
	// print 메서드
	// num, shape 모양에 맞춰서 출력하는 메서드
	public void print() {
		if (shape == '♥' || shape == '♣' || shape == '◆' || shape == '♠' ) {
			if (0 < num && num < 14) {
				switch (num) {
				case 11:
					System.out.println(shape +""+ 'J'); // char + char = 아스키코드상 번호로 결과 출력
					break;
				case 12:
					System.out.println(shape + "Q");
					break;
				case 13:
					System.out.println(shape + "K");
					break;
				default:
					System.out.println(shape +""+ num);
					break;
				}
			}
		}else {
			shape = '♥';
			num = 1;
			System.out.println(shape +""+ num);
		}
	}
	public char getShape() {
		return shape;
	}
	public void setShape(char shape) {
		this.shape = shape;
	}
	public int getNum() {
		return num;
	}
	public void setNum(int num) {
		this.num = num;
	}
	
}

CardPack Class

/* Card 클래스 생성
 * - 숫자 : 1 ~ 10 , J, Q, K
 * - 모양 : ♥, ◆, ♣, ♠
 * - 한 장의 카드 정보를 출력하는 기능
 * 
 *  클래스의 구성
 *  - 멤버변수 : 모양, 숫자 => preivate선언 => getter/setter생성
 *  - 메서드 : print 메서드
 *  - 생성자 : 기본생성자만 생성 => ♥1
 */
public class Card {
	private char shape;
	private int num;
	
	// 생성자는 설정하지 않아도 기본 생성자 제공
	// 생성자는 객체 생성시 (new)에만 작동
	// Card c = new Card();  // Card(); 생성자
	 public Card() {
		shape = '♥';
		num = 1;
	}
	
	public void print() {
		System.out.print(shape);
		switch (num) {
		case 11:
			System.out.print('J' + " ");
			break;
		case 12:
			System.out.print('Q' + " ");
			break;
		case 13:
			System.out.print('K' + " ");
			break;
		default:
			System.out.print(num +" ");
			break;
		}
	
	}

	public char getShape() {
		return shape;
	}
	//  ♥, ◆, ♣, ♠
	public void setShape(char shape) {
		switch (shape) {
		case '♥': case '◆': case '♣': case '♠':
			this.shape = shape;
			break;
		default:
			this.shape = '♥';
			break;
		}
//		if (shape.equals("♥") || shape.equals("◆") || shape.equals("♣") || shape.equals("♠")) {
//			this.shape = shape;
//		}
//		else {
//			this.shape = "♥";
//		}
	}

	public int getNum() {
		return num;
	}

	public void setNum(int num) {
		if (0 < num && num < 14) { // 1 ~ 13까지만 저장
			this.num = num;
		}
		else {
			this.num = 1; // 아니면 기본값 1
		}
	}
	
}
/* CardPack 클래스
 * - 52장의 카드 한 묶음(배열)
 * 
 * - 카드 섞는 기능
 * - 한장의 카드를 빼내는 기능 > 확인
 * - 출력 기능 > Card 클래스에서 사용
 * - 카드 초기화 기능
 */
public class CardPack {
	private Card[] pack = new Card[52]; // 52장의 카드가 들어갈 수 있는 배열
	private int cnt = 0; // 카드의 남는 개수
	
	public CardPack() {
		char shape = '♥'; // ♥ ◆ ♣ ♠
		for (int i = 1; i <= 4; i++) {
			switch (i) {
			case 1 : shape = '♥'; break; 
			case 2 : shape = '◆'; break;  
			case 3 : shape = '♣'; break;  
			case 4 : shape = '♠'; break;
			}
			for (int j = 1; j <= 13; j++) {
				Card  c = new Card();
				c.setShape(shape);
				c.setNum(j);
				pack[cnt] = c;
				cnt++;
			}
		}
	}
	// pick 카드 한장 빼내는 기능
	// pick()
	// 현재 cnt 값은?
	// cnt = 0이라는 의미는 카드가 하나도 생성되지 않은 상황
	// 리턴타입 Card
	public Card pick() {
		if (cnt == 0) {
			return null;
		}
		cnt--;
		return pack[cnt];
	}
	
	// 카드를 섞는 기능
	// shuffle();
	// 리턴타입 : void, 매개변수 : x
	public void shuffle() {
		int min = 0;
		int max = pack.length-1; // 0 ~ 51번지
		for (int i = 0; i < pack.length; i++) {
			int random = (int)(Math.random()*(max - min +1))+min;
			Card tmp = pack[i];
			pack[i] = pack[random];
			pack[random] = tmp;
		}
	}
	
	// 초기화 기능
	public void init() {
		cnt = 52;
	}
	
}
public class CardPrint {

	public static void main(String[] args) {
		Card c = new Card();
//		c.print();
//		c.setNum(13);
//		c.setShape('♠');
//		c.print();
//		c.setNum(14);
//		c.setShape('&');
//		c.print();
		
		CardPack pack = new CardPack();
		pack.shuffle(); // 카드 섞기
		
		for (int i = 1; i <= 4; i++) { // 4줄로 출력
			for (int j = 1; j <= 13; j++) { // 모양대로 13개씩
				Card tmp = pack.pick();
				tmp.print();
			}
			System.out.println(); // 줄바꿈
		}
		
		pack.init();
		pack.pick().print();
		
		
	}

}
public class _01_Class6_Ex1 {

	public static void main(String[] args) {
		// Car class를 활용한 생성자 연습
		Car c = new Car();
		c.setName("Tiguan");
		c.setColor("White");
		c.setYear("2016/6");
		c.setDoor("4Door");
		c.setAirback("4EA");
		c.printInfo();
		Car c1 = new Car("Zeta", "Blue", "2020/3");
		c1.printInfo();
		Car c2 = new Car("Porsche", "Red", "2023/5", "2Door");
		c2.printInfo();
		Car c3 = new Car("Benz", "Black", "2018/12", "4Door", "4EA");
		Car c4 = new Car("Benz", "Gray", "2022/2", "4Door", "4EA", true, 200);
		System.out.println("--c3--");
		c3.printInfo();
		c3.powerOnOff();
		
		c3.speedUp();
		c3.speedUp();
		c3.speedUp();
		c3.setSpeed(200);
		c3.speedUp();
		c3.speedUp();
		c3.speedDown();
		c3.speedDown();
		c3.setSpeed(0);
		c3.speedDown();
		c3.speedDown();
		System.out.println("--c4--");
		c4.printInfo();
		c4.speedUp();
		c4.speedDown();
		c4.speedDown();
		//toString 호출
		System.out.println("--toString()--");
		System.out.println(c4);
//		System.out.println(c4.toString()); // 위와 동일
	}

}
// Car class 작성 위치
class Car{
	private String name;
	private String color;
	private String year;
	private String door;
	private String airback;
	private boolean power;
	private int speed;
	
	// 멤버변수 : name, color, year, door, airback, power, speed
	// 멤버변수 생성 => getter / setter 생성
	// 생성자 : 기본생성자
	
	
	
	
	public Car() {} // 기본생성자
	// 생성자2 : name, color, year 받는 생성자
	public Car(String name, String color, String year) {
		this.name = name;
		this.color = color;
		this.year = year;
	}
	// 생성자3 : name, color, year, door 받는 생성자
	public Car(String name, String color, String year, String door) {
		// 생성자 호출
		this(name, color, year); // 생성자 호출은 반드시 첫줄에 해야함
//		this.name = name;
//		this.color = color;
//		this.year = year;
		this.door = door;
	}
	// 생성자4 : name, color, year, door, airback  받는 생성자
	public Car(String name, String color, String year, String door, String airback) {
		// 생성자 호출
		this(name, color, year, door); // 생성자 호출은 반드시 첫줄에 해야함
//		this.name = name;
//		this.color = color;
//		this.year = year;
//		this.door = door;
		this.airback = airback;
	}
	// 전체 받는 생성자
	public Car(String name, String color, String year, String door, String airback, boolean power, int speed) {
		//super();  // 상속자가 가지고 있는 생성자
		this.name = name;
		this.color = color;
		this.year = year;
		this.door = door;
		this.airback = airback;
		this.power = power;
		this.speed = speed;
	}
	// 메서드
	// printInfo() : name, color, year, door, airback 출력
	public void printInfo() {
		System.out.printf("Car Info%nname : %s%ncolor : %s%nyear : %s%ndoor : %s%nairback : %s%n", 
				name, color, year, door, airback);
		System.out.println("----------------");
	}
	// toString() : 
	@Override
	public String toString() {
		return "Car [name=" + name + ", color=" + color + ", year=" + year + ", door=" + door + ", airback=" + airback
				+ "]";
	}
	
	// powerOnOff()
	public void powerOnOff() {
		power = !power;
	}

	// speedUp()
	public void speedUp() {
		int max = 200;
		if (power) {
			if (speed == max) {
				System.out.println("SPEED MAX : " + max);
				speed = max;
			} else {
				speed += 10;
				System.out.println("SPEED(+) : " + speed);
			}
		}
	}
	// speedDown()
	public void speedDown() {
		int stop = 0;
		if (power) {
			if (speed == stop) {
				System.out.println("STOP");
				speed = stop;
			} else {
				speed -= 10;
				System.out.println("SPEED(-) : " + speed);
			}
		}
	}
	// getter/setter 생성
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public String getColor() {
		return color;
	}
	public void setColor(String color) {
		this.color = color;
	}
	public String getYear() {
		return year;
	}
	public void setYear(String year) {
		this.year = year;
	}
	public String getDoor() {
		return door;
	}
	public void setDoor(String door) {
		this.door = door;
	}
	public String getAirback() {
		return airback;
	}
	public void setAirback(String airback) {
		this.airback = airback;
	}
	public boolean isPower() {
		return power;
	}
	public void setPower(boolean power) {
		this.power = power;
	}
	public int getSpeed() {
		return speed;
	}
	public void setSpeed(int speed) {
		this.speed = speed;
	}
	
}
public class _02_Class7_Ex2 {

	public static void main(String[] args) {
		/* static이 붙은 멤버변수/메서드를 클래스 멤버변수/메서드 라고 한다
		/* static이 붙지 않음 멤버변수/메서드를 인스턴스(객체) 멤버변수/메서드 라고 한다
		 * - 객체 멤버변수/메서드는 객체를 통해 사용되고, 생성된다.
		 * - 각 객체마다 독립적인 변수/메서드가 된다.
		 * 
		 * - 클래스 멤버변수/메서드는 클래스를 통해 사용된다. (클래스명.메서드(변수))
		 * - 객체를 통해 호출되는 것이 가능하나 일반적으로 사용하지 않는다.
		 * - 클래스 멤버변수는 하나의 멤버변수를 모든 객체가 공유(사용)한다.
		 * 
		 * - 클래스 / 객체는 생성 시점이 달라서 메서드에 사용될수 있는 환경이 다르다.
		 * - 객체 멤버는 이미 클래스가 생성되고 난 후 객체를 생성해야 생성
		 * - 클래스 멤버는 클래스를 생성할 시점에 메모리에 생성
		 * - 클래스 멤버는 클래스의 멤버(변수&메서드) / 객체의 멤버(변수/메서드)에서 모두 사용할수 있다.
		 * - 객체의 멤버는 객체에서만 사용될수 있다.
		 * 
		 * final : 최종의. 마지막의, 더이상 변경할 수 없는
		 * - final은 클래스, 변수, 메서드에 붙일 수 있다.
		 * - final 멤버 변수 : 상수(수정할수 없는 값)
		 * - final 멤버 메서드 : 오버라이딩(재정의)할 수 없다.
		 * - final 클래스 : 상속(확장)할 수 없다.
		 */
		Tv t = new Tv();
		// 객체 멤버 메서드 접근 방식 : 객체 생성 후 객체명.메서드명();
		t.printPower();
		System.out.println("-------------");
		
		// 클래스명으로 직접 접근(클래스 멤버들은 객체를 생성해서 접근하지 않음)
		// 클래스 멤버 메서드 접근 방식 : 클래스명.메서드명();
		Tv.printBrand();
		

	}

}
class Tv {
	private boolean power;
	private final static String brand = "Apple";
	
	public void printPower() {
		if(power) {
			System.out.println("TV가 켜졌습니다.");
		}
		else {
			System.out.println("TV가 꺼졌습니다.");
		}
		// 인스턴스 메서드에서 클래스 변수를 사용한 경우
		System.out.println("브랜드 : " + brand);
	}
	public static void printBrand()	{
		// 메서드에 static을 붙이는 경우는 인스턴스 멤버를 사용할 일이 없는 경우
		System.out.println("브랜드 : " + brand); // 가능한 경우
		// 클래스 메서드에서 인스턴스 변수를 사용한 경우 error
//		System.out.println("전원상태 : " + power); // 불가능한 경우
	}
}

 

public class _03_Class8_Ex3 {

	public static void main(String[] args) {
		/* 클래스 생성시 값을 초기화하는 방법
		 * - 기본값, 명시적 초기값, 초기화블럭, 생성자
		 * 1. 기본값 : 기본적으로 지정된 값 int => 0, String => null, boolean => false
		 * 2. 명시적 초기값 : 멤버변수 선언과 동시에 값을 지정하는 방법
		 *	private String name = "홍길동";
		 * 3. 초기화 블럭 : {  } 멤버변수의 초기화
		 * 4. 생성자 : 객체를 생성할 때 초기화 해서 생성
		 * - 초기값들의 우선순위
		 * 기본값(우선순위 낮음) -> 명시적 초기값 -> 초기화 블럭 -> 생성자(우선순위 높음)
		 */
		EzenStudent e = new EzenStudent();
		e.setName("홍길동");
		e.setClassroom("JAVA class");
		e.setPhoneNumber("010-123-4567");
		System.out.println(e);
	}

}
class EzenStudent {
	// 멤버변수 : 지점="incheon", 이름, 반, 전화번호
	private String branch = "incheon"; // 명시적 초기값
	private String name; // 기본값 : null
	private String classroom;
	private String phoneNumber;
	
	{
		// 초기화 블럭 영역
		branch = "인천";
		classroom = "미정";
	}
	
	
	// 생성자
	public EzenStudent() {}
	// using fields 사용 생성자
	public EzenStudent(String branch, String name, String classroom, String phoneNumber) {
		super();
		this.branch = branch;
		this.name = name;
		this.classroom = classroom;
		this.phoneNumber = phoneNumber;
	}

	// print 메서드(toString 가능)
	@Override
	public String toString() {
		return "EzenStudent [branch : " + branch + ", name : " + name + ", classroom : " + classroom + ", phoneNumber : "
				+ phoneNumber + "]";
	}
	// getter / setter

	public String getBranch() {
		return branch;
	}

	public void setBranch(String branch) {
		this.branch = branch;
	}

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getClassroom() {
		return classroom;
	}

	public void setClassroom(String classroom) {
		this.classroom = classroom;
	}

	public String getPhoneNumber() {
		return phoneNumber;
	}

	public void setPhoneNumber(String phoneNumber) {
		this.phoneNumber = phoneNumber;
	}
	
}
public class EzenComputer1 {
	//멤버 변수 선언
	private String name;
	private String birth;
	private String age;
	private String phone;
	private final String COMPANY = "EZEN"; // final은 대문자로 처리
	private String branch;
	private String[] course = new String[5]; // 수강과목
	private String[] period = new String[5]; // 기간
	private int cnt; // 배열의 index 처리용
	
	// 생성자
	public EzenComputer1() {}
	
	public EzenComputer1(String name, String phone, String branch) {
		this.name = name;
		this.phone = phone;
		this.branch = branch;
	}
	public EzenComputer1(String name, String phone, String branch, String birth, String age) {
		this(name, phone, branch);
		this.birth = birth;
		this.age = age;
	}
	// 메서드
	public void printInfo()	{
		System.out.println("--학생정보--");
		System.out.println("이름:"+name+", age:"+age+"세");
		System.out.println("tel:"+phone+", 생년월일:"+birth);
	}
	public void printCompany() {
		System.out.println("==학원정보==");
		System.out.println("학원명:"+COMPANY+", 지점:"+branch);
	}
	
	public void printCourse() { // 배열 -> for 반복하여 출력
		if(course.length == 0 || cnt == 0) {
			System.out.println("수강과목이 없습니다.");
			return;
		}
		// cnt까지만 출력 => 추가되지 않은 값은 출력x
		for (int i = 0; i < cnt; i++) { // 수강과목 => 1과목
			System.out.println("과정:"+course[i]+"("+period[i]+")");
		}
	}
	// 수강정보 등록 => insertCourse() 한번 호출하면 1과목 등록
	public void insertCourse(String course, String period) {
		// cnt = 0 => 아직 추가값 없음
		if (cnt >= 5) {
			System.out.println("더이상 수강할 수 없습니다.");
			return;
		}
		this.course[cnt] = course;
		this.period[cnt] = period;
		cnt++; // 1개 담고 번지 증가
	}
	// getter / setter

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public String getBirth() {
		return birth;
	}

	public void setBirth(String birth) {
		this.birth = birth;
	}

	public String getAge() {
		return age;
	}

	public void setAge(String age) {
		this.age = age;
	}

	public String getPhone() {
		return phone;
	}

	public void setPhone(String phone) {
		this.phone = phone;
	}

	public String getBranch() {
		return branch;
	}

	public void setBranch(String branch) {
		this.branch = branch;
	}

	public String[] getCourse() {
		return course;
	}

	public void setCourse(String[] course) {
		this.course = course;
	}

	public String[] getPeriod() {
		return period;
	}

	public void setPeriod(String[] period) {
		this.period = period;
	}

	public int getCnt() {
		return cnt;
	}

	public void setCnt(int cnt) {
		this.cnt = cnt;
	}

	public String getCOMPANY() {
		return COMPANY;
	}
	
}
public class EzenPrint {

	public static void main(String[] args) {
//		EzenComputer e = new EzenComputer();
//		e.setName("홍길동");
//		e.setBirthDate("880820");
//		e.setAge("36");
//		e.setPhoneNumber("010-123-4567");
//		e.studentInfo();
//		
//		e.setBranch("인천");
//		e.schoolInfo();
//
//		e.addClasses("자바", "2023-01 ~ 2023-04");
//		e.addClasses("파이썬", "2023-04 ~ 2023-05");
//		e.addClasses("자바스크립트", "2023-04 ~ 2023-08");
//		e.addClasses("자바", "2023-07 ~ 2023-10");
//		e.classesInfo();
		
		EzenComputer1 ec = new EzenComputer1();
		ec.setName("철수");
		ec.setAge("36");
		ec.setBirth("880101");
		ec.setPhone("010-111-1111");
		ec.setBranch("인천");
//		ec.printCompany();
//		ec.printInfo();
		ec.insertCourse("java", "1개월");
		ec.insertCourse("python", "1개월");
		ec.insertCourse("js", "1개월");
		ec.insertCourse("html", "1개월");
		ec.insertCourse("css", "1개월");
//		ec.printCourse();
//		System.out.println("-----------------------");
		EzenComputer1 ec2 = new EzenComputer1("영희","010-222-2222","인천","890202","35");
//		ec2.printInfo();
		ec2.insertCourse("java", "2개월");
		ec2.insertCourse("python", "2개월");
		ec2.insertCourse("js", "2개월");
		ec2.insertCourse("html", "2개월");
		ec2.insertCourse("css", "2개월");
//		ec2.printCourse();
//		System.out.println("-----------------------");
		EzenComputer1 ec3 = new EzenComputer1("순식","010-333-3333","인천","900202","34");
//		ec3.printInfo();
		ec3.insertCourse("java", "3개월");
		ec3.insertCourse("python", "3개월");
		ec3.insertCourse("js", "3개월");
		ec3.insertCourse("html", "3개월");
		ec3.insertCourse("css", "3개월");
//		ec3.printCourse();
//		System.out.println("-----------------------");
		EzenComputer1 ec4 = new EzenComputer1("홍식","010-444-4444","서울","910202","33");
//		ec4.printInfo();
		ec4.insertCourse("java", "4개월");
		ec4.insertCourse("python", "4개월");
		ec4.insertCourse("js", "4개월");
		ec4.insertCourse("html", "4개월");
		ec4.insertCourse("css", "4개월");
//		ec4.printCourse();
//		System.out.println("-----------------------");
		EzenComputer1 ec5 = new EzenComputer1("영순","010-555-5555","서울","920202","32");
//		ec5.printInfo();
		ec5.insertCourse("java", "5개월");
		ec5.insertCourse("python", "5개월");
		ec5.insertCourse("js", "5개월");
		ec5.insertCourse("html", "5개월");
		ec5.insertCourse("css", "5개월");
//		ec5.printCourse();
//		System.out.println("-----------------------");
		EzenComputer1 ec6 = new EzenComputer1("희철","010-666-6666","서울","930202","31");
//		ec6.printInfo();
		ec6.insertCourse("java", "6개월");
		ec6.insertCourse("python", "6개월");
		ec6.insertCourse("js", "6개월");
		ec6.insertCourse("html", "6개월");
		ec6.insertCourse("css", "6개월");
//		ec6.printCourse();
//		System.out.println("-----------------------");
		EzenComputer1 ec7 = new EzenComputer1("정숙","010-777-7777","서울","940202","30");
//		ec7.printInfo();
		ec7.insertCourse("java", "7개월");
		ec7.insertCourse("python", "7개월");
		ec7.insertCourse("js", "7개월");
		ec7.insertCourse("html", "7개월");
		ec7.insertCourse("css", "7개월");
//		ec7.printCourse();
//		System.out.println("-----------------------");
		
		
		/* 숙제
		 * 배열로 5명의 학생 등록 후  // 마음대로 등록
		 * - 이름으로 검색(어느 지점(학원정보)의 무슨과목(수강정보)을 듣고 있는지 출력)
		 * - 지점으로 검색(지점(학원정보)에 있는 학생(학생정보)들 모두 출력)
		 */
		EzenComputer1[] std = new EzenComputer1[7];
		std[0] = ec;
		std[1] = ec2;
		std[2] = ec3;
		std[3] = ec4;
		std[4] = ec5;
		std[5] = ec6;
		std[6] = ec7;
		
		Scanner scan = new Scanner(System.in);
		System.out.println("학생이름으로 검색");
		String val = scan.next();
		// 이름 : 철수, 영희, 순식, 홍식, 영순, 희철, 정숙 // 지점 : 인천, 서울
		// 이름으로 검색
		System.out.println("학생이름 : " + val);
		int cnt = 0;
		for (EzenComputer1 ez : std) {
			if (ez.getName().equals(val)) {
				ez.printCompany();
				ez.printCourse();
				cnt++;
			}
		}
		if (cnt == 0) {
			System.out.println("등록되지 않은 학생입니다.");
		}
		System.out.println("------------------------");
		// 지점으로 검색
		System.out.println("지점으로 검색");
		val = scan.next();
		System.out.println("지점 : " + val);
		cnt = 0;
		for (EzenComputer1 ez : std) {
			if (ez.getBranch().equals(val)) {
				ez.printCompany();
				ez.printInfo();
				ez.printCourse();
				cnt++;
			}
		}
		if (cnt == 0) {
			System.out.println("등록되지 않은 지점입니다.");
		}
		
	}

}