C++ Exspresso 제5장 클래스의 기초
이번 장에서 학습할 내용 클래스와 객체 객체의 일생 메소드 필드 UML 직접 클래스를 작성해 봅시다.
먼저 앞장에서 학습한 클래스와 객체의 개념을 복습해봅시다. QUIZ 먼저 앞장에서 학습한 클래스와 객체의 개념을 복습해봅시다. 속성 동작 객체는 ________과 _________을 가지고 있다. 자동차가 객체라면 클래스는 ________이다. 설계도
1. 클래스의 구성 클래스(class)는 객체의 설계도라 할 수 있다. 클래스는 멤버 변수와 멤버 함수로 이루어진다. 멤버 변수는 객체의 속성을 나타낸다. 멤버 함수는 객체의 동작을 나타낸다.
추상화 추상화는 많은 특징 중에서 문제 해결에 필요한 것만을 남기고 나머지는 전부 삭제하는 과정이다.
클래스 정의의 예 class Car { public: // 멤버 변수 선언 int speed; // 속도 int gear; // 기어 string color; // 색상 // 멤버 함수 선언 void speedUp() { // 속도 증가 멤버 함수 speed += 10; } void speedDown() { // 속도 감소 멤버 함수 speed -= 10; }; 멤버 변수 정의! 멤버 함수 정의!
객체 int 타입의 변수를 선언하는 경우 int i; 클래스도 타입으로 생각하면 된다. Car 타입의 변수를 선언하면 객체가 생성된다. Car myCar;
객체의 사용 객체를 이용하여 멤버에 접근할 수 있다. 이들 멤버 변수에 접근하기 위해서는 도트(.) 연산자를 사용한다. myCar.speed = 100; myCar.speedUp(); myCar.speedDown();
예제 #include <iostream> #include <string> using namespace std; class Car { public: // 멤버변수선언 int speed; // 속도 int gear; // 기어 string color; // 색상 // 멤버함수선언 void speedUp() { // 속도증가멤버함수 speed += 10; } void speedDown() { // 속도감소멤버함수 speed -= 10; };
예제 int main() { Car myCar; myCar.speed = 100; myCar.gear = 3; myCar.color = "red"; myCar.speedUp(); myCar.speedDown(); return 0; }
여러 개의 객체 생성 #include <iostream> #include <string> using namespace std; class Car { public: int speed; // 속도 int gear; // 기어 string color; // 색상 void speedUp() { // 속도증가멤버함수 speed += 10; } void speedDown() { // 속도감소멤버함수 speed -= 10; void show() { // 상태출력멤버함수 cout << "============== " << endl; cout << "속도: " << speed << endl; cout << "기어: " << gear << endl; cout << "색상: " << color << endl; };
예제 int main() { Car myCar, yourCar; myCar.speed = 100; myCar.gear = 3; myCar.color = "red"; yourCar.speed = 10; yourCar.gear = 1; yourCar.color = "blue"; myCar.speedUp(); yourCar.speedUp(); myCar.show(); yourCar.show(); return 0; }
예제 ============== 속도: 110 기어: 3 색상: red 속도: 20 기어: 1 색상: blue
객체의 동적 생성 객체도 new와 delete를 사용하여서 동적으로 생성, 반환할 수 있다. Car *dynCar = new Car; // 동적 객체 생성 dynCar->speed = 100; // 동적 객체 사용 dynCar->speedUp(); // 동적 객체 사용 ... delete dynCar; // 동적 객체 삭제
중간 점검 문제 1. 객체들을 만드는 설계도에 해당되는 것이 _____________이다. 2. 클래스 선언 시에 클래스 안에 포함되는 것은 _____과 ______이다. 3. 객체의 멤버에 접근하는데 사용되는 연산자는 ________이다. 4. 강아지를 나타내는 클래스를 작성하여 보라. 강아지의 이름, 종, 색깔 등을 멤버 변수로 지정하고 짖기, 물기, 먹기 등의 멤버 함수를 정의하여 보라. 5. 동적 메모리 할당을 이용하여서 otherCar를 생성하는 문장을 쓰시오. 6. 객체 포인터 p를 통하여 getSpeed() 멤버 함수를 호출하는 문장을 쓰시오.
2. 접근 제어
전용 멤버와 공용 멤버 전용 멤버(private member) 비공개 멤버 클래스 내부에서만 접근이 허용 공용 멤버(public member) 공개 멤버 공용 멤버는 다른 모든 클래스들이 사용 가능
private와 public 아무것도 지정하지 않으면 디폴트로 private 객체를 통해 직접 접근할 수 없다!!! class Car { // 멤버 변수 선언 int speed; // 속도 int gear; // 기어 string color; // 색상 } int main() { Car myCar; myCar.speed = 100; // 오류! 아무것도 지정하지 않으면 디폴트로 private 객체를 통해 직접 접근할 수 없다!!!
private와 public 다른 지정자가 나오기 전까지 public class Car { public: int speed; // 속도 int gear; // 기어 string color; // 색상 } int main() { Car myCar; myCar.speed = 100; // OK! 다른 지정자가 나오기 전까지 public
private와 public class Car { public: int speed; // 공용 멤버 private: int gear; // 전용 멤버 string color; // 전용 멤버 }
예제 #include <iostream> #include <string> using namespace std; class Employee { string name; // private 로 선언 int salary; // private 로 선언 int age; // private 로 선언 // 직원의 월급을 반환 int getSalary() { return salary; } public: // 직원의 나이를 반환 int getAge() { return age; } // 직원의 이름을 반환 string getName() { return name; } }; int main() { Employee e; e.salary = 300; // 오류! private 변수 e.age = 26; // 오류! private 변수 int sa = e.getSalary(); // 오류! private 멤버함수 string s = e.getName(); // OK! int a = e.getAge(); // OK }
멤버 변수 멤버 변수: 클래스 안에서 그러나 멤버 함수 외부에서 정의되는 변수 class Date { public: void printDate() { cout << year << "." << month << "." << day << endl; } int getDay() { return day; // 멤버 변수 선언 int year; string month; int day; }
중간 점검 문제 1. 접근 제어 지시어인 private와 public을 설명하라. 2. 아무런 접근 제어 지시어를 붙이지 않으면 어떻게 되는가?
3. 접근자와 설정자 접근자(accessor): 멤버 변수의 값을 반환 (예) getBalance() 설정자(mutator): 멤버 변수의 값을 설정 (예) setBalance();
예제 class Car { private: // 멤버 변수 선언 int speed; //속도 int gear; //기어 string color; //색상 ... public: // 접근자 선언 int getSpeed() { return speed; } // 설정자 선언 void setSpeed(int s) { speed = s;
예제 // 접근자 선언 int getGear() { return gear; } // 변경자 선언 void setGear(int g) { gear = g; string getColor() { return color; void setColor(string c) { color = c; };
접근자와 설정자의 장점 설정자의 매개 변수를 통하여 잘못된 값이 넘어오는 경우, 이를 사전에 차단할 수 있다. 멤버 변수값을 필요할 때마다 계산하여 반환할 수 있다. 접근자만을 제공하면 자동적으로 읽기만 가능한 멤버 변수를 만들 수 있다. void setSpeed(int s) { if( s < 0 ) speed = 0; else speed = s; }
중간 점검 문제 1. 접근자와 설정자 함수를 사용하는 이유는 무엇인가? 2. 강아지(종, 나이, 몸무게)를 클래스로 모델링하고 각 멤버 변수에 대하여 접근자와 설정자를 작성하여 보라.
4. 멤버 함수의 외부 정의
내부 정의와 외부 정의의 차이 멤버 함수가 클래스 내부에서 정의되면 자동적으로 인라인(inline) 함수가 된다. 멤버 함수가 클래스 외부에 정의되면 일반적인 함수와 동일하게 호출한다.
예제 #include <iostream> using namespace std; class Car { public: int getSpeed(); void setSpeed(int s); void honk(); private: int speed; //속도 }; int Car::getSpeed() { return speed; } void Car::setSpeed(int s) speed = s;
예제 빵빵! 현재 속도는 80 계속하려면 아무 키나 누르십시오 . . . void Car::honk() { cout << "빵빵!" << endl; } int main() Car myCar; myCar.setSpeed(80); myCar.honk(); cout << "현재 속도는" << myCar.getSpeed() << endl; return 0; 빵빵! 현재 속도는 80 계속하려면 아무 키나 누르십시오 . . .
클래스 선언과 구현의 분리 클래스의 선언과 구현을 분리하는 것이 일반적
예제 car.h 클래스를 선언한다. class Car { public: int getSpeed(); void setSpeed(int s); void honk(); private: int speed; //속도 }; car.h 클래스를 선언한다.
예제 car.cpp 클래스를 정의한다. #include <iostream> #include "car.h" using namespace std; int Car::getSpeed() { return speed; } void Car::setSpeed(int s) speed = s; void Car::honk() cout << "빵빵!" << endl; car.cpp 클래스를 정의한다.
예제 main.cpp 클래스를 사용한다. #include <iostream> #include "car.h" // 현재위치에car.h를읽어서넣으라는것을의미한다. using namespace std; int main() { Car myCar; myCar.setSpeed(80); myCar.honk(); cout << "현재속도는" << myCar.getSpeed() << endl; return 0; } main.cpp 클래스를 사용한다.
5. 멤버 함수의 중복 정의 멤버 함수도 중복 정의(오버로딩:Overloading)가 가능함 class Car { private: int speed; //속도 int gear; //기어 string color; //색상 public: int getSpeed(); void setSpeed(int s); void setSpeed(double s); }; 함수의 중복시 함수 이름이 같지만 함수의 signature(매개변수의 개수, 자료형)는 반드시 달라야 한다!!!
멤버 함수의 중복 정의 int Car::getSpeed() { return speed; } void Car::setSpeed(int s) { speed = s; void Car::setSpeed(double s) { speed = (int)s; int main() { Car myCar; myCar.setSpeed(80); myCar.setSpeed(100.0); cout << "차의 속도: " << myCar.getSpeed() << endl; return 0; 멤버 함수 중복 정의
6. 자동차 경주 예제 간단한 자동차 게임을 작성 두 대의 자동차를 생성하여서 속도를 0에서 199사이의 난수로 설정 속도가 빠른 자동차가 무조건 경주에서 이긴다고 가정
예제 #include <iostream> #include <string> using namespace std; class Car { private: int speed; //속도 int gear; //기어 string color; //색상 public: int getSpeed(); // 외부에서 정의 void setSpeed(int s); int getGear(); void setGear(int g); string getColor(); void setColor(string c); void speedUp(); void speedDown(); void init(int s, int gear, string c); void show(); };
예제 int Car::getSpeed() { return speed; } void Car::setSpeed(int s) { speed = s; int Car::getGear() { return gear; void Car::setGear(int g) { gear = g; string Car::getColor() { return color; void Car::setColor(string c) { color = c; void Car::speedUp() { // 속도증가멤버함수 speed += 10;
예제 void Car::speedUp() { // 속도증가멤버함수 speed += 10; } void Car::speedDown() { // 속도감소멤버함수 speed -= 10; void Car::init(int s, int g, string c) { speed = s; gear = g; color = c; void Car::show() { cout << "============== " << endl; cout << "속도: " << speed << endl; cout << "기어: " << gear << endl; cout << "색상: " << color << endl;
예제 int main() { Car car1, car2; car1.init(rand() % 200, 1, "red"); car1.show(); car2.init(rand() % 200, 1, "red"); car2.show(); if( car1.getSpeed() > car2.getSpeed() ) cout << "car1이 승리하였습니다" << endl; else cout << "car2가 승리하였습니다" << endl; return 0; } ============== 속도: 41 기어: 1 색상: red 속도: 67 색상: blue car2가 승리하였습니다
중간 점검 문제 1. 멤버 함수 안에서 private 멤버 변수를 사용할 수 있는가? 2. 멤버 함수는 클래스의 외부에서 정의될 수 있는가? 3. 멤버 함수는 별도의 소스 파일에서 정의될 수 있는가?
UML UML(Unified Modeling Language): 애플리케이션을 구성하는 클래스들간의 관계를 그리기 위하여 사용 use use Is_A 클래스 + public, - private
클래스와 클래스의 관계
구조체 구조체(structure) = 클래스 struct BankAccount { // 은행계좌 int accountNumber; // 계좌번호 int balance; // 잔액을표시하는변수 double interest_rate; // 연이자 double get_interrest(int days){ return (balance*interest_rate)*((double)days/365.0); } }; 모든 멤버가 디폴트로 public이 된다.
예제(Desk Lamp)
예제 (Desk Lamp) #include <iostream> #include <string> using namespace std; class DeskLamp { private: // 인스턴스변수정의 bool isOn; // 켜짐이나꺼짐과같은램프의상태 public: // 멤버함수선언 void turnOn(); // 램프를켠다. void turnOff(); // 램프를끈다. void print(); // 현재상태를출력 }; void DeskLamp::turnOn() { isOn = true; }
예제 (Desk Lamp) 램프가 켜짐 램프가 꺼짐 void DeskLamp::turnOff() { isOn = false; } void DeskLamp::print() cout << "램프가" << (isOn == true ? "켜짐" : "꺼짐") << endl; int main() // 객체생성 DeskLamp lamp; // 객체의멤버함수를호출하려면도트연산자인.을사용한다. lamp.turnOn(); lamp.print(); lamp.turnOff(); return 0; 램프가 켜짐 램프가 꺼짐
예제 (BankAccount) 은행 계좌
예제 #include <iostream> #include <string> using namespace std; class BankAccount { // 은행계좌 private: int accountNumber; // 계좌번호 string owner; // 예금주 int balance; // 잔액을표시하는변수 public: void setBalance(int amount); // balance에대한설정자 int getBalance(); // balance에대한접근자 void deposit(int amount); // 저금함수 void withdraw(int amount); // 인출함수 void print(); // 현재상태출력 }; void BankAccount::setBalance(int amount) { balance = amount; }
예제 잔액은 10000입니다. 잔액은 2000입니다. int BankAccount::getBalance() { return balance; } void BankAccount::deposit(int amount) balance += amount; void BankAccount::withdraw(int amount) balance -= amount; void BankAccount::print() cout << "잔액은" << balance << "입니다." << endl; int main() { BankAccount account; account.setBalance(0); account.deposit(10000); account.print(); account.withdraw(8000); return 0; 잔액은 10000입니다. 잔액은 2000입니다.
예제(Date) 날짜 1
예제(Date) #include <iostream> #include <string> using namespace std; class Date { private: int year; int month; int day; public: int getYear(); void setYear(int y); int getMonth(); void setMonth(int m); void setDay(int d); int getDay(); void print(); }; int Date::getYear() { return year; }
예제(Date) 2010년 1월 20일 void Date::setYear(int y) { year = y; } int Date::getMonth() { return month; } void Date::setMonth(int m) { month = m; } int Date::getDay() { return day; } void Date::setDay(int d) { day = d; } void Date::print() { cout << year << "년" << month << "월" << day << "일" << endl; } int main() Date date; date.setYear(2010); date.setMonth(1); date.setDay(20); date.print(); return 0; 2010년 1월 20일
예제(Product) 상품
예제 #include <iostream> #include <string> using namespace std; class Product { private: int id; string name; int price; public: void input(); void print(); bool isCheaper(Product other); }; void Product::input() { cout << "상품의일련번호: "; cin >> id; cout << "상품의이름: "; cin >> name; cout << "상품의가격: "; cin >> price; }
예제 void Product::print() { cout << " 상품번호" << id << endl << " 상품의이름: " << name << " 상품의가격: " << price << endl; } bool Product::isCheaper(Product other) if( price < other.price ) return true; else return false;
예제 int main() { Product p1, p2; p1.input(); p2.input(); if( p1.isCheaper(p2) ){ p1.print(); cout << "이더쌉니다\n"; } else { p2.print(); return 0; 상품의 일련 번호: 1 상품의 이름: 모니터 상품의 가격: 100000 상품의 일련 번호: 2 상품의 이름: 컴퓨터 상품의 가격: 20000000 상품 번호 1 상품의 이름: 모니터 상품의 가격: 100000 이 더 쌉니다
Exercise 8. 다음은 영화를 나타내는 Movie 클래스이다. 질문에 답하라. 1) UML class Movie { string title; // 영화제목 string director; // 감독 string actors; // 배우 }
2) 각 멤버 변수에 대한 접근자와 설정자를 작성하라. string getTitle(){ return title; } string getDirector(){ return director; string getActors(){ return actors; void setTitle(string m_t) { title = m_t; } void setDirector(string m_d) director = m_d; void setActors(string m_a) actors = m_a;
3) 추가할 수 있는 멤버 변수와 멤버함수를 추가하라. string grade; //등급 string genre; // 장르 4) C++로 작성하라. 5) 객체 title 속성을 “transformer”로 변경하라. 6) Movie 객체를 세 개 작성하라. 각각의 값을 멤버함수를 이용하여 변경하라. 7) Movie 객체의 내용을 출력하는 show() 멤버 함수를 작성하고, Show() 함수 호출을 통해 객체를 출력하라.
Programming 4. Employee 클래스 작성. - 직원이름 - 전화번호 - 연봉 접근자와 설정자를 작성하라.
Programming 8. 본문의 BankAccount 클래스에서 송금하는 멤버함수를 추가한 다음 검사하는 프로그램을 작성하라. int BankAccount::transfer(int amount, BankAccount otherAccount) { … }
int main(){ BankAccount account, account1; account int main(){ BankAccount account, account1; account.setBalance(0); account1.setBalance(0); account.deposit(100000); account1.deposit(1000); cout<<"계좌 1의 잔액은>> "; account.print(); cout<<"계좌 2의 잔액은>> "; account1.print(); account.withdraw(8000); cout<<"-> 계좌 1에서 2000원을 계좌 2로 이체하기"<<endl; cout<<"계좌 1에 이체한 후 잔액은 : "<<account.transfer(2000, account1)<<endl; return 0; }
Q & A