C++ 초급 - 7. 구조체와 클래스 (2 - 클래스 (class vs struct))

2025. 2. 22. 14:00프로그래밍 언어/C++

📌 7.2 클래스 (class vs struct)

C++에서는 struct와 class 모두 데이터와 함수를 포함할 수 있는 사용자 정의 자료형이다.
하지만 객체 지향 프로그래밍(OOP, Object-Oriented Programming)을 활용하려면 클래스(class)를 사용하는 것이 일반적이다.

주요 차이점

  • struct → 기본 접근 지정자(public), 단순한 데이터 저장 목적.
  • class → 기본 접근 지정자(private), 캡슐화 및 OOP 지원.

📌 1. struct와 class의 차이점

🔹 (1) 기본 접근 지정자 차이

💡 예제: struct vs class

#include <iostream>

struct StructExample {
    int x;  // 기본 접근 지정자가 public
};

class ClassExample {
    int x;  // 기본 접근 지정자가 private

public:
    void setX(int val) { x = val; }
    int getX() { return x; }
};

int main() {
    StructExample s;
    s.x = 10;  // ✅ 직접 접근 가능 (public)

    ClassExample c;
    // c.x = 20;  // ❌ private 멤버에 직접 접근 불가능
    c.setX(20);  // ✅ setter를 통해 값 설정

    std::cout << "struct x: " << s.x << std::endl;
    std::cout << "class x: " << c.getX() << std::endl;

    return 0;
}

🔹 출력 결과

struct x: 10
class x: 20

💡 설명

  • struct → 기본 접근 지정자가 public이므로, s.x = 10; 가능.
  • class → 기본 접근 지정자가 private이므로, c.x = 20; 불가능.

📌 2. 객체 선언 및 초기화

🔹 (1) 클래스 선언 및 객체 생성

💡 기본 문법

class 클래스이름 {
private:
    데이터타입 변수명;

public:
    함수명();
};

💡 예제: 클래스 선언 및 초기화

#include <iostream>

class Car {
private:
    std::string brand;
    int year;

public:
    // 생성자(Constructor)
    Car(std::string b, int y) {
        brand = b;
        year = y;
    }

    // 멤버 함수
    void printInfo() {
        std::cout << "브랜드: " << brand << ", 연식: " << year << std::endl;
    }
};

int main() {
    Car car1("Toyota", 2022);
    Car car2("BMW", 2021);

    car1.printInfo();
    car2.printInfo();

    return 0;
}

🔹 출력 결과

브랜드: Toyota, 연식: 2022
브랜드: BMW, 연식: 2021

💡 설명

  • class Car { ... }; → 클래스 선언.
  • Car car1("Toyota", 2022); → 생성자를 이용한 객체 초기화.
  • car1.printInfo(); → 클래스 멤버 함수 호출.

📌 3. 클래스를 사용한 캡슐화 및 데이터 보호

🔹 (1) 캡슐화(Encapsulation)란?

캡슐화객체의 내부 데이터를 외부에서 직접 접근하지 못하도록 보호하는 개념이다.

  • private → 클래스 내부에서만 접근 가능 (외부에서 접근 불가).
  • public → 어디서든 접근 가능.
  • protected → 상속받은 클래스에서 접근 가능.

💡 예제: 캡슐화 적용

#include <iostream>

class BankAccount {
private:
    int balance;  // 외부에서 직접 접근 불가

public:
    BankAccount(int b) { balance = b; }

    void deposit(int amount) { balance += amount; }
    void withdraw(int amount) {
        if (amount <= balance) balance -= amount;
        else std::cout << "잔액 부족" << std::endl;
    }

    int getBalance() { return balance; }  // private 멤버 접근을 위한 메서드
};

int main() {
    BankAccount account(1000);

    account.deposit(500);
    std::cout << "잔액: " << account.getBalance() << std::endl;  // 1500

    account.withdraw(2000);  // 잔액 부족
    std::cout << "잔액: " << account.getBalance() << std::endl;  // 1500

    return 0;
}

🔹 출력 결과

잔액: 1500
잔액 부족
잔액: 1500

💡 설명

  • balance는 private → 직접 접근 불가.
  • getBalance(), deposit(), withdraw() → 캡슐화를 통해 안전한 데이터 관리.

📌 4. 객체 배열 및 포인터 활용

🔹 (1) 객체 배열

💡 예제: 객체 배열

#include <iostream>

class Student {
private:
    std::string name;
    int age;

public:
    Student(std::string n, int a) { name = n; age = a; }
    void printInfo() { std::cout << name << " (" << age << "세)" << std::endl; }
};

int main() {
    Student students[2] = {Student("Alice", 20), Student("Bob", 22)};

    for (int i = 0; i < 2; i++) {
        students[i].printInfo();
    }

    return 0;
}

🔹 출력 결과

Alice (20세)
Bob (22세)

💡 설명

  • Student students[2] = { ... }; → 객체 배열 선언 및 초기화.
  • students[i].printInfo(); → 배열 요소 접근 방식.

🔹 (2) 객체 포인터 활용

💡 예제: 객체 포인터 사용

#include <iostream>

class Animal {
public:
    std::string name;

    Animal(std::string n) { name = n; }
    void printName() { std::cout << "동물 이름: " << name << std::endl; }
};

int main() {
    Animal* ptr = new Animal("Tiger");  // 객체 동적 할당
    ptr->printName();

    delete ptr;  // 동적 할당 해제
    return 0;
}

🔹 출력 결과

동물 이름: Tiger

💡 설명

  • Animal* ptr = new Animal("Tiger"); → 객체를 동적 할당.
  • ptr->printName(); → 객체 포인터를 통한 멤버 함수 호출.
  • delete ptr; → 메모리 해제 필수.

📌 5. 정리

개념  설명
struct vs class struct: 기본 public, class: 기본 private
객체 생성 클래스이름 변수명(값1, 값2);
캡슐화 private 멤버 보호, public 메서드를 통해 접근
객체 배열 클래스이름 배열명[크기] = {...};
객체 포인터 클래스이름* 변수명 = new 클래스이름();