C, C++ 콘솔 입력 간단 비교

  • C언어 콘솔 입력
scanf("%d %d %s", &month, &date, &todos);
  • C++언어 콘솔 입력
cin >> month >> date >> todos;

C언어에서의 scanf를 통한 입력은 경계검사를 하지 않기때문에 안전하지 않았다.

C++의 cin은 scanf를 어느정도 대체하였는데, 차이는

null 스트링 < - > stream 스트링 의 차이이다.

  • null 스트링 : 마지막 비트가 null. 하나하나 읽으면서 null이면 그만 읽는 식. 표현하기위해 비트 하나가 필요(null 비트)
  • stream 스트링 : 헤더에 길이값이 있는 것. 정해진 길이만 읽음. 길이비트 필요. null 스트링보다 비트가 많이 필요하지만 빠르게 읽을 수 있다.(정해진 크기의 값을 바로 읽기 때문)

C++언어에서 사용

# include <iostream>
using namespace std;

int main()
{
    int month;
    int date;

    cin >> month >> date;
}

cin도 똑같이 메모리 할당 이슈가 있다

c언어보다 표현이 보다 쉬워지고 안전해졌지만 그래도 메모리 할당이슈는 여전했는데,

char input[4];
cin >> input;  // input의 길이를 모른다.

이와 같이 컴퓨터 입장으로서는 정해진 입력해야되는 변수의 정확한 크기를 모를 때 발생할 수 있다.

해결하는 방법은

char input[4];
cin >> setw(4) >> input;

과 같이 미리 잘라두는 것.

스트림 상태 확인

우리가 stream을 사용할때 stream 상태를 확인 할수가 있는데,

C언어에서

if (fgets(line, 10, stdin) != NULL)
{
    // todo
}

와 표현했었다.

C++에서는 다음과 같이 확인 할 수 있다.

cin >> line;
if (!cin.eof())
{
    // todo
}

istream 상태확인 메서드

네임스페이스 - ios_base

  • good()
  • eof()
  • fail()
  • bad()

를 통해 steam 상태를 확인 할 수 있다.

입력값을 통한 비교

int number;
cin >> number;

와 같이 한다고 가정해보자.

우선 입력값에 따른 eofbit와 failbit는 다음과 같다.

입력값 eofbit failbit
456abc unset unset
456 (un)set unset
abc unset set
eof set set

기본적으로 숫자를 읽는것이기 때문에 문자가 나오면 멈추는데,

  • 첫번째 - 456을 읽고 a에서 포인터가 멈춰있는 상태. 일단 456이라는 숫자는 읽어서 값으로 들어가있다. 그래서 실패하지는 않아서 failbit가 unset 하지만, 끝나지도 않았으므로 eofbit도 unset
  • 두번째 - 456을 읽고 456 뒷 부분에 포인터가 위치(다 읽은 상태) 그래서 eofbit set. failbit unset. (un)set이라 한 이유는 가끔 unset이 될 때가 있다. 이럴때는 입력버리기를 사용해야 된다.
  • 세번째 - abc 문자에서 a에 포인터가 멈춰있는 상태. 숫자값도 아닐뿐더러 읽은 값이 없어서 failbit set, eofbit unset
  • 네번째 - eof를 읽긴 했으므로 eofbit는 set되나, 숫자값이 아니므로 failbit set

입력 버리기(Discarding Input)

입력상태 (스트림상태)를 무시하고, 버리고 다시 입력받고 싶을 때 사용한다.

  • cin.clear() - 스트림을 good 상태로 돌려줌.
  • cin.ignore() - 문자 1개를 버림
  • cin.ignore(10) - 문자 10개를 버림

ignore는 eof에 도달하거나 지정한 수만큼 버리면 멈춘다.

  • cin.ignore(10, ‘\n’) - 문자 10개를 버리거나 newline을 만나면 멈춤.
  • cin.ingore(LLONG_MAX, ‘\n’) - 최대 문자 수 (한 줄) 를 버리거나 newline을 만나면 멈춤.

입력 함수

get() 함수

뉴라인 문자, 혹은 설정문자를 만나기 직전까지의 모든 문자를 가져온다.

뉴라인 문자는 입력스트림에 남아있다.

get(firstName, 100); // 99개 문자 혹은 newline까지의 문자.
get(firstName, 100, '#') // 99개 문자 혹은 '#' 문자가 나올때까지.
getline() 함수

뉴라인 문자 혹은 설정문자를 만나기 직전까지의 모든 문자를 가져온다.

뉴라인 문자는 입력스트림에서 버린다.

getline(firstName, 100); // 99개 문자 혹은 newline까지의 문자.
getline(firstName, 100, '#') // 99개 문자 혹은 '#' 문자가 나올때까지.

차이점은 뉴라인을 버리냐 마냐

정리

  1. 입력스트림
  2. `>> 연산자
  3. 스트림 상태 (파일 입력에서도 쓰임)
  4. 입력 버리기 (파일 입력에서도 쓰임)