출시·고도화 중
C++ 안내서 · 3/6
C++는 정적 타입 언어입니다. 모든 값의 타입이 컴파일할 때 정해지며, 컴파일러는 이를 바탕으로 오류를 찾고 효율적인 코드를 만듭니다. 이 장에서는 기본 타입, 문자열, 표준 컨테이너, 그리고 직접 타입을 만드는 클래스·구조체·열거형을 다룹니다.
| 타입 | 설명 | 예 |
|---|---|---|
bool | 참/거짓 | true, false |
char | 문자 한 개(1바이트) | 'A' |
int | 부호 있는 정수(보통 32비트) | 42 |
long long | 64비트 이상 정수 | 9'000'000'000LL |
double | 배정밀도 부동소수점 | 3.14 |
std::size_t | 크기·인덱스용 부호 없는 정수 | v.size()의 반환 타입 |
int의 크기는 표준이 정확히 정하지 않습니다. 비트 수가 중요하다면 <cstdint>의 std::int32_t, std::uint64_t 같은 고정 크기 타입을 씁니다. 숫자 사이의 작은따옴표(')는 C++14부터 쓸 수 있는 자릿수 구분자입니다.
C 스타일 문자 배열 대신 <string>의 std::string을 쓰면 메모리를 직접 관리할 필요가 없습니다.
#include <iostream>
#include <string>
int main() {
std::string s{"Hello"};
s += ", world"; // 이어 붙이기
std::cout << s.size() << '\n'; // 12
std::cout << s.substr(0, 5) << '\n'; // "Hello"
if (auto pos = s.find("world"); pos != std::string::npos) {
std::cout << "찾은 위치: " << pos << '\n';
}
int n = std::stoi("123"); // 문자열 -> 정수
std::string t = std::to_string(n + 1); // 정수 -> 문자열
}읽기만 하는 문자열 인자는 const std::string& 또는 C++17의 std::string_view로 받습니다. std::string_view는 원본을 복사하지 않고 가리키기만 하므로, 원본보다 오래 살아남지 않게 주의해야 합니다.
| 컨테이너 | 특징 |
|---|---|
std::vector<T> | 크기가 늘어나는 연속 배열. 기본 선택 |
std::array<T, N> | 크기가 컴파일 시간에 고정된 배열 |
std::map<K, V> | 키 순서로 정렬된 연관 배열 |
std::unordered_map<K, V> | 해시 기반 연관 배열. 순서 없음 |
#include <array>
#include <iostream>
#include <map>
#include <string>
#include <vector>
int main() {
std::vector<int> nums{3, 1, 4};
nums.push_back(1);
std::cout << nums.size() << ' ' << nums[0] << '\n'; // 4 3
std::array<double, 3> point{1.0, 2.0, 3.0};
std::cout << point.at(2) << '\n'; // at() 은 범위를 검사합니다
std::map<std::string, int> stock;
stock["apple"] = 5;
stock["banana"] = 2;
for (const auto& [name, qty] : stock) { // C++17 구조적 바인딩
std::cout << name << ": " << qty << '\n';
}
if (stock.contains("apple")) { /* C++20 */ }
}[]는 범위를 검사하지 않으므로 잘못된 인덱스는 정의되지 않은 동작이 됩니다. 확실하지 않을 때는 at()을 쓰거나 크기를 먼저 확인합니다. std::map의 []는 없는 키를 넣으면 기본값으로 새 항목을 만든다는 점도 기억해 둡니다.
클래스는 데이터(멤버 변수)와 동작(멤버 함수)을 묶습니다. private 멤버는 클래스 밖에서 접근할 수 없어서, 객체가 항상 올바른 상태를 유지하도록 지킬 수 있습니다.
#include <stdexcept>
#include <string>
#include <utility>
class Account {
public:
explicit Account(std::string owner, long long balance = 0)
: owner_{std::move(owner)}, balance_{balance} { // 멤버 초기화 목록
if (balance_ < 0) throw std::invalid_argument("음수 잔액");
}
void deposit(long long amount) { balance_ += amount; }
long long balance() const { return balance_; } // const 멤버 함수
const std::string& owner() const { return owner_; }
private:
std::string owner_;
long long balance_;
};
// Account a{"Kim", 1000};
// a.deposit(500); // a.balance() == 1500생성자는 멤버 초기화 목록으로 멤버를 초기화합니다. explicit은 인자 하나짜리 생성자가 원치 않는 자동 변환에 쓰이지 않게 막습니다. 객체를 바꾸지 않는 멤버 함수에는 const를 붙여 const 객체에서도 부를 수 있게 합니다.
struct는 기본 접근 권한이 public이라는 점만 class와 다릅니다. 관례적으로 불변 조건이 없는 단순한 데이터 묶음에 씁니다. enum class는 이름 범위가 분리되고 정수로 자동 변환되지 않는 안전한 열거형입니다.
#include <string>
enum class Color { Red, Green, Blue };
struct Pixel {
int x = 0;
int y = 0;
Color color = Color::Red;
};
std::string to_string(Color c) {
switch (c) {
case Color::Red: return "red";
case Color::Green: return "green";
case Color::Blue: return "blue";
}
return "unknown";
}
// Pixel p{10, 20, Color::Blue}; // 집합체 초기화
// int raw = static_cast<int>(p.color); // 정수가 필요하면 명시적으로 변환<cstdint>의 고정 크기 타입을 씁니다.std::string, 읽기 전용 인자는 const std::string&이나 std::string_view를 씁니다.std::vector를 기본으로, 고정 크기는 std::array, 키-값은 std::map/std::unordered_map을 씁니다.class와 private 멤버로, 단순 데이터는 struct로 만듭니다.enum class를 씁니다.
댓글 0개
로그인 · 로그인하면 댓글을 남길 수 있습니다.
첫 댓글을 남겨 보세요.