icon안동민 개발노트

스트림과 파일 입출력 개요


스트림의 개념

 스트림은 입력과 출력을 추상화한 개념으로, 데이터의 흐름을 나타냅니다. C++에서 스트림은 다양한 종류의 입출력 작업을 일관된 인터페이스로 처리할 수 있게 해줍니다.

 주요 특징

  • 순차적인 데이터 접근
  • 입력 소스와 출력 대상의 추상화
  • 다양한 데이터 타입에 대한 자동 형변환

표준 입출력 스트림

 C++는 네 가지 표준 스트림을 제공합니다.

  1. cin : 표준 입력 스트림
  2. cout : 표준 출력 스트림
  3. cerr : 표준 에러 스트림 (버퍼링되지 않음)
  4. clog : 표준 로그 스트림 (버퍼링됨)
예제
#include <iostream>
#include <string>
 
int main() {
    std::string name;
    int age;
 
    std::cout << "이름을 입력하세요: ";
    std::getline(std::cin, name);
 
    std::cout << "나이를 입력하세요: ";
    std::cin >> age;
 
    std::cout << "안녕하세요, " << name << "님! " << age << "세 이시군요." << std::endl;
 
    std::cerr << "이것은 에러 메시지입니다." << std::endl;
    std::clog << "이것은 로그 메시지입니다." << std::endl;
 
    return 0;
}

파일 스트림

 파일 입출력을 위해 C++는 다음 클래스를 제공합니다.

  1. ifstream : 파일 입력 스트림
  2. ofstream : 파일 출력 스트림
  3. fstream : 파일 입출력 스트림
예제
#include <fstream>
#include <iostream>
#include <string>
 
int main() {
    // 파일 쓰기
    std::ofstream outFile("example.txt");
    if (outFile.is_open()) {
        outFile << "Hello, File I/O!" << std::endl;
        outFile << "This is a test." << std::endl;
        outFile.close();
    } else {
        std::cerr << "파일을 열 수 없습니다." << std::endl;
        return 1;
    }
 
    // 파일 읽기
    std::ifstream inFile("example.txt");
    if (inFile.is_open()) {
        std::string line;
        while (std::getline(inFile, line)) {
            std::cout << line << std::endl;
        }
        inFile.close();
    } else {
        std::cerr << "파일을 열 수 없습니다." << std::endl;
        return 1;
    }
 
    return 0;
}

문자열 스트림

 문자열 스트림을 사용하면 문자열을 스트림처럼 처리할 수 있습니다.

  1. istringstream : 문자열 입력 스트림
  2. ostringstream : 문자열 출력 스트림
  3. stringstream : 문자열 입출력 스트림
예제
#include <sstream>
#include <iostream>
#include <string>
 
int main() {
    std::stringstream ss;
    ss << "Age: " << 25 << ", Height: " << 180.5;
    std::cout << "문자열 스트림 내용: " << ss.str() << std::endl;
 
    int age;
    double height;
    std::string dummy;
    ss >> dummy >> age >> dummy >> height;
 
    std::cout << "파싱된 정보 - 나이: " << age << ", 키: " << height << std::endl;
 
    return 0;
}

입출력 조작자

 입출력 조작자를 사용하여 스트림의 형식을 제어할 수 있습니다.

#include <iostream>
#include <iomanip>
 
int main() {
    double pi = 3.14159265359;
 
    std::cout << "기본 출력: " << pi << std::endl;
    std::cout << "고정 소수점 (6자리): " << std::fixed << std::setprecision(6) << pi << std::endl;
    std::cout << "과학적 표기법: " << std::scientific << pi << std::endl;
    std::cout << "필드 폭 지정: " << std::setw(10) << std::right << pi << std::endl;
 
    return 0;
}

파일 모드

 파일을 열 때 다양한 모드를 지정할 수 있습니다.

  • ios::in : 읽기 모드
  • ios::out : 쓰기 모드
  • ios::app : 추가 모드
  • ios::ate : 파일 끝에서 시작
  • ios::trunc : 파일 내용 삭제
  • ios::binary : 이진 모드
예제
#include <fstream>
#include <iostream>
 
int main() {
    std::ofstream outFile("data.txt", std::ios::out | std::ios::app);
    if (outFile.is_open()) {
        outFile << "This is appended text." << std::endl;
        outFile.close();
    }
 
    return 0;
}

연습 문제

  1. 사용자로부터 학생 정보(이름, 나이, 성적)를 입력받아 파일에 저장하고, 나중에 이 파일을 읽어 모든 학생의 평균 성적을 계산하는 프로그램을 작성하세요.
  2. 주어진 텍스트 파일에서 특정 단어의 출현 빈도를 계산하는 프로그램을 작성하세요.


참고 자료

  • C++ 공식 문서의 입출력 라이브러리 섹션 : Input/output library
  • "C++ Primer" by Stanley B. Lippman, Josée Lajoie, and Barbara E. Moo (Chapter 8 : The IO Library)
  • "The C++ Programming Language" by Bjarne Stroustrup (Chapter 38 : I/O Streams)
  • C++ Core Guidelines의 입출력 관련 규칙 : I/O rule summary
  • "Effective C++" by Scott Meyers (Item 29 : Consider issues of exception safety when writing streams)