본문 바로가기

카테고리 없음

입력 버퍼 클리어하기: scanf와 fgets를 혼합하여 사용할 때

왜 "청소"가 필요한가?

컴퓨터와 이야기할 때, 우리는 키보드를 사용해서 컴퓨터에게 무엇을 해야 하는지 알려준다. 가끔은 숫자를 입력하라고 하고, 가끔은 글자나 문장을 입력하라고 한다. 이때 컴퓨터는 우리가 누른 키보드의 모든 것을 기억하는데, 그 중에는 엔터 키도 포함된다. 엔터 키는 컴퓨터에게 프로그램을 끝냈다는 신호이다. 

문제가 생기는 상황

상상해보자. 당신이 컴퓨터에게 숫자를 입력하고 엔터를 쳤다고 가정하자. 그 다음에 문장을 입력하라고 했는데, 컴퓨터가 너무 빨리 반응해서 아무것도 입력하지 않았는데도 바로 넘어가버린다면 어떨까? 이건 마치 당신이 친구와 말하기도 전에 친구가 네 말을 끊고 넘어가는 것처럼 답답한 상황인 것이다. 

 

이처럼 scanf 함수는 사용자로부터 특정 형식의 데이터를 입력받는 데 사용된다. 그러나 scanf로 데이터를 입력받은 후 사용자가 엔터 키를 누르면 줄바꿈 문자(\n)가 입력 버퍼에 남게 된다. 이후 fgets 함수를 사용하여 문자열을 입력받으려 하면, fgets는 버퍼에 남은 줄바꿈 문자를 만나자마자 입력을 종료한다고 판단하고 빈 문자열을 반환할 수 있다. 이는 fgets가 줄의 끝을 입력의 끝으로 간주하기 때문이다.

 

이 문제는 컴퓨터가 너가 처음 숫자를 입력하고 엔터를 친 것까지 기억하고 있다가, 문장을 입력할 차례가 되면 이미 엔터 키를 눌렀다고 생각해서 그냥 넘어가버리기 때문에 발생한다. 

버퍼클리어로 "청소"하는 방법

이 문제를 해결하기 위해서는, 숫자를 입력하고 엔터를 친 후, 문장을 입력하기 전에 컴퓨터의 기억에서 엔터 키를 지워줘야 한다. 이것을 우리는 "입력 버퍼 청소하기"라고 할 수 있다. 버퍼란 컴퓨터가 잠시 데이터를 저장하는 곳이다. 

"청소"하는 방법은 간단하다. 컴퓨터에게 엔터 키를 포함해 지금까지 기억하고 있는 모든 것을 잊어버리라고 하는 것이다. 그래야만 우리가 다음에 말하는 것을 제대로 듣고 반응할 수 있다. 

 

ClearLineFromReadBuffer 함수의 역할

ClearLineFromReadBuffer 함수는 이러한 문제를 해결하기 위한 간단하면서도 효과적인 방법이다. 이 함수는 입력 버퍼를 순회하며 줄바꿈 문자를 만날 때까지 getchar() 함수를 사용해 문자를 하나씩 소비한다. 줄바꿈 문자를 만나는 순간 함수는 종료되며, 입력 버퍼가 클리어된다. 결과적으로, 이 함수는 다음 입력을 받기 위해 버퍼를 깨끗한 상태로 유지한다.

void ClearLineFromReadBuffer(void)
{
    while(getchar() != '\n');
}

사용 사례

다음은 ClearLineFromReadBuffer 함수를 사용하는 예시다. 사용자로부터 정수를 scanf로 입력받고, 이후 fgets를 사용해 문자열을 안전하게 입력받고자 할 때, scanf와 fgets 사이에 ClearLineFromReadBuffer 함수를 호출한다.

#include <stdio.h>

void ClearLineFromReadBuffer(void);

int main(void) {
    int number;
    char string[100];

    printf("Enter a number: ");
    scanf("%d", &number);

    ClearLineFromReadBuffer();

    printf("Enter a string: ");
    fgets(string, sizeof(string), stdin);

    // 이후 처리
    return 0;
}

void ClearLineFromReadBuffer(void) {
    while(getchar() != '\n');
}

 

이 방식을 사용하면, scanf를 통해 정수 입력을 받은 후, fgets로 문자열을 안전하게 입력받을 수 있다. ClearLineFromReadBuffer 함수는 입력 버퍼의 상태를 관리하며, scanf와 fgets를 혼합하여 사용할 때 발생할 수 있는 문제를 방지한다.

 

사용자로부터의 입력 처리는 프로그래밍에서 흔히 마주치는 작업이다. 특히, C 언어에서는 scanf와 fgets를 혼합하여 사용할 때 주의가 필요하다. ClearLineFromReadBuffer 함수는 이러한 상황에서 입력 버퍼를 효과적으로 관리할 수 있는 간단한 해결책을 제공한다