[C++] Stream

초연·2023년 3월 19일
0

CPP

목록 보기
1/3

정의

스트림(Stream)이란 유저로 하여금 순서가 있는 데이터 원소의 집합을 읽고 쓸 수 있도록 캡슐화한 자료구조이다.

입출력 라이브러리

streambuf

모든 입출력 객체는 입출력 데이터를 캐싱하는 스트림 버퍼를 갖고, C++도 스트림 버퍼에 대응되는 streambuf 클래스가 있다.

char, wchar_t 등 여러 크기의 문자를 모두 처리할 수 있어서 편리하다.

streambuf 클래스는 스트림 버퍼의 시작과 끝을 가리키는 포인터와 다음에 참조할 위치를 가리키는 포인터(스트림 위치 지정자)를 갖는다.

입출력 버퍼 각각을 get area, put area라 부르며, 버퍼를 가리키는 포인터에 g와 p를 붙인다.

Example

Code

#include <iostream>
#include <string>

int main()
{
	std::string s;
    std::cout << "Enter your full name: ";

    std::cin >> s;
    /* 시점 A */
    std::cout << "First name: " << s << std::endl;

	/* 입력 스트림 버퍼(get area)의 포인터 반환 */
	if (auto* gbuf = std::cin.rdbuf())
    {
    	/* 스트림 위치 지정자를 한 칸 전진 및 해당 위치 문자 반환 */
        char c = gbuf->snextc();
        /* 시점 B */
        std::cout << "Preview: " << c << std::endl;
    }

	std::cin >> s;
    /* 시점 C */
    std::cout << "Last name: " << s << std::endl;
}

Result

  1. 시점 A
    문자열은 공백 전까지만 읽으므로 s = "Choyeon"이고, 스트림 위치 지정자는 공백을 가리킨다.
  1. 시점 B
    스트림 위치 지정자를 한 칸 전진시켰으므로 K를 가리킨다.
  1. 시점 C
    K부터 공백 전까지 읽으므로 s = "Kim"이고, 스트림 위치 지정자는 문자열의 끝을 가리킨다.

ios_base

ios_base 클래스는 실수 타입의 정밀도 같은 스트림의 입출력 형식 데이터를 처리한다.

입출력 형식을 지정하려면, ios_base::hex 같은 형식 플래그(Format Flag)를 setf 함수에 전달해 호출하거나 std::hex 같은 조작자(Maniulator)를 호출한다.

ios

ios 클래스는 스트림 버퍼를 초기화하고, 4개의 플래그로 스트림의 상태를 관리한다.

FlagDescription
goodbit입출력 가능
failbit복구 가능 오류
badbit복구 불가능 오류
eofbitEOF(End Of File) 도달

입력 값의 타입 불일치 같은 오류 발생 시, 스트림 버퍼를 비우지 않고 반환한다.

따라서, 다음 입력 값도 스트림 버퍼 값을 사용하므로 입력할 수 없어서 연쇄적인 오류가 발생한다.

fail 함수는 failbit 또는 badbit가 true이면, true를 반환한다.

fail 함수가 true를 반환하면, clear 함수로 플래그를 초기화 및 ignore 함수로 스트림 버퍼를 비운다.

fstream

파일 입출력 스트림 클래스다.

OptionDescription
ios::inRead Mode
ios::outWrite Mode
ios::binaryBinary Mode
ios::appInsert Mode, 스트림 위치 지정자는 파일의 끝에 위치
ios::ateOverwrite Mode, 스트림 위치 지정자는 파일의 끝에 위치
ios::trunc기존 내용 삭제

Example

Code

#include <fstream>
#include <iostream>
#include <string>

int main()
{
	std::fstream file;

	/* 파일 연결 시도 */
    file.open("file.txt", std::ios::app);

	/* 파일 연결 검사 */
    if (!file.is_open())
    {
    	std::cout << "Can't open!" << std::endl;
        return 0;
    }

	/* 파일에 쓰기 */
    file << "Choyeon Kim";

	/* 스트림 위치 지정자의 위치로 파일의 크기 계산 */
    int size = file.tellg();

	/* 스트림 위치 지정자를 파일의 처음으로 이동 */
    file.seekg(0, std::ios::beg);

	/* 파일을 읽기 */
    std::string s;
    file.read(&s[0], size);
    std::cout << s << std::endl;

	/* 파일 연결 종료 */
	file.close();
}
profile
게임 클라이언트 프로그래머

0개의 댓글

관련 채용 정보